summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Android.mk28
-rw-r--r--api/current.txt59
-rw-r--r--api/removed.txt2
-rw-r--r--api/system-current.txt7
-rw-r--r--api/test-current.txt68
-rw-r--r--cmds/idmap2/Android.bp2
-rw-r--r--cmds/idmap2/include/idmap2/Result.h124
-rw-r--r--cmds/idmap2/libidmap2/Idmap.cpp14
-rw-r--r--cmds/idmap2/libidmap2/Result.cpp41
-rwxr-xr-xcmds/idmap2/static-checks.sh1
-rw-r--r--cmds/idmap2/tests/IdmapTests.cpp4
-rw-r--r--cmds/idmap2/tests/RawPrintVisitorTests.cpp4
-rw-r--r--cmds/idmap2/tests/ResultTests.cpp288
-rw-r--r--cmds/statsd/src/atom_field_options.proto2
-rw-r--r--cmds/statsd/src/atoms.proto26
-rw-r--r--cmds/statsd/src/guardrail/StatsdStats.cpp5
-rw-r--r--cmds/statsd/src/guardrail/StatsdStats.h6
-rw-r--r--cmds/statsd/src/metrics/CountMetricProducer.cpp1
-rw-r--r--cmds/statsd/src/metrics/DurationMetricProducer.cpp1
-rw-r--r--cmds/statsd/src/metrics/EventMetricProducer.cpp1
-rw-r--r--cmds/statsd/src/metrics/GaugeMetricProducer.cpp1
-rw-r--r--cmds/statsd/src/metrics/MetricsManager.cpp57
-rw-r--r--cmds/statsd/src/metrics/MetricsManager.h4
-rw-r--r--cmds/statsd/src/metrics/ValueMetricProducer.cpp5
-rw-r--r--cmds/statsd/src/metrics/ValueMetricProducer.h4
-rw-r--r--cmds/statsd/src/stats_log.proto1
-rw-r--r--cmds/statsd/src/stats_log_util.cpp3
-rw-r--r--cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp315
-rw-r--r--cmds/svc/src/com/android/commands/svc/PowerCommand.java4
-rw-r--r--config/hiddenapi-greylist.txt1
-rw-r--r--core/java/android/app/ActivityThread.java22
-rw-r--r--core/java/android/content/Intent.java22
-rw-r--r--core/java/android/content/pm/PackageInfo.java18
-rw-r--r--core/java/android/content/pm/PackageParser.java88
-rw-r--r--core/java/android/content/pm/PermissionInfo.java10
-rw-r--r--core/java/android/content/pm/UsesPermissionInfo.java275
-rw-r--r--core/java/android/content/res/AssetManager.java10
-rw-r--r--core/java/android/content/res/Resources.java62
-rw-r--r--core/java/android/content/res/ResourcesImpl.java26
-rw-r--r--core/java/android/hardware/camera2/CameraCharacteristics.java73
-rw-r--r--core/java/android/hardware/camera2/CameraDevice.java18
-rw-r--r--core/java/android/hardware/camera2/CaptureRequest.java16
-rw-r--r--core/java/android/hardware/camera2/CaptureResult.java16
-rw-r--r--core/java/android/hardware/camera2/impl/CameraMetadataNative.java22
-rw-r--r--core/java/android/hardware/camera2/params/StreamConfigurationMap.java151
-rw-r--r--core/java/android/hardware/display/NightDisplayListener.java153
-rw-r--r--core/java/android/net/ConnectivityManager.java19
-rw-r--r--core/java/android/net/IConnectivityManager.aidl2
-rw-r--r--core/java/android/os/BatterySaverPolicyConfig.java44
-rw-r--r--core/java/android/os/IPowerManager.aidl2
-rw-r--r--core/java/android/os/PowerManager.java160
-rw-r--r--core/java/android/provider/Settings.java8
-rw-r--r--core/java/android/service/dreams/Sandman.java3
-rw-r--r--core/java/android/text/TextLine.java3
-rw-r--r--core/java/android/view/AccessibilityInteractionController.java79
-rw-r--r--core/java/android/view/RemotableViewMethod.java3
-rw-r--r--core/java/android/view/SurfaceControl.java25
-rw-r--r--core/java/android/view/SurfaceView.java8
-rw-r--r--core/java/android/view/View.java166
-rw-r--r--core/java/android/view/ViewRootImpl.java28
-rw-r--r--core/java/android/view/WindowManagerPolicyConstants.java34
-rw-r--r--core/java/android/view/accessibility/AccessibilityManager.java3
-rw-r--r--core/java/android/view/accessibility/AccessibilityNodeIdManager.java68
-rw-r--r--core/java/android/view/autofill/AutofillId.java2
-rw-r--r--core/java/android/view/autofill/AutofillManager.java3
-rw-r--r--core/java/android/view/contentcapture/ContentCaptureEvent.java5
-rw-r--r--core/java/android/view/contentcapture/ViewNode.java16
-rw-r--r--core/java/android/view/inputmethod/InputMethodManager.java12
-rw-r--r--core/java/android/widget/AbsListView.java19
-rw-r--r--core/java/android/widget/Magnifier.java2
-rw-r--r--core/java/android/widget/TextView.java4
-rw-r--r--core/java/com/android/internal/os/ZygoteConnection.java9
-rw-r--r--core/jni/android_util_AssetManager.cpp41
-rw-r--r--core/jni/android_view_Surface.cpp43
-rw-r--r--core/jni/android_view_SurfaceControl.cpp3
-rw-r--r--core/jni/include/android_runtime/android_view_Surface.h3
-rw-r--r--core/proto/android/providers/settings/global.proto2
-rw-r--r--core/res/AndroidManifest.xml69
-rw-r--r--core/res/res/values/attrs.xml2
-rw-r--r--core/res/res/values/attrs_manifest.xml79
-rw-r--r--core/res/res/values/config.xml4
-rw-r--r--core/res/res/values/public.xml10
-rw-r--r--core/tests/coretests/src/android/provider/SettingsBackupTest.java1
-rw-r--r--core/tests/coretests/src/android/view/accessibility/FindViewByIdTest.java100
-rw-r--r--core/tests/coretests/src/android/view/contentcapture/ContentCaptureEventTest.java229
-rw-r--r--core/tests/coretests/src/android/view/contentcapture/UserDataRemovalRequestTest.java88
-rw-r--r--core/tests/coretests/src/android/view/contentcapture/ViewNodeTest.java376
-rw-r--r--data/etc/privapp-permissions-platform.xml10
-rw-r--r--graphics/java/android/graphics/ImageFormat.java9
-rw-r--r--graphics/java/android/graphics/Typeface.java6
-rw-r--r--libs/androidfw/AssetManager2.cpp22
-rw-r--r--libs/androidfw/include/androidfw/AssetManager2.h6
-rw-r--r--location/java/android/location/GnssMeasurement.java57
-rw-r--r--media/java/android/media/Image.java7
-rw-r--r--media/java/android/media/ImageReader.java2
-rw-r--r--media/java/android/media/ImageUtils.java7
-rw-r--r--media/java/android/media/audiopolicy/AudioMix.java9
-rw-r--r--media/jni/android_media_MediaCodec.cpp7
-rw-r--r--media/jni/android_media_MediaCodec.h1
-rw-r--r--media/jni/android_media_MediaCodecList.cpp138
-rw-r--r--media/jni/android_media_Utils.cpp24
-rw-r--r--media/jni/android_media_Utils.h2
-rw-r--r--packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java19
-rw-r--r--packages/PrintSpooler/AndroidManifest.xml12
-rw-r--r--packages/SettingsProvider/src/com/android/providers/settings/SettingsProtoDumpUtil.java3
-rw-r--r--packages/SystemUI/AndroidManifest.xml5
-rw-r--r--packages/SystemUI/res/raw/image_wallpaper_fragment_shader.glsl33
-rw-r--r--packages/SystemUI/res/raw/image_wallpaper_vertex_shader.glsl8
-rw-r--r--packages/SystemUI/src/com/android/systemui/Dependency.java6
-rw-r--r--packages/SystemUI/src/com/android/systemui/DependencyProvider.java6
-rw-r--r--packages/SystemUI/src/com/android/systemui/ImageWallpaper.java159
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java50
-rw-r--r--packages/SystemUI/src/com/android/systemui/doze/DozeService.java3
-rw-r--r--packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLProgram.java115
-rw-r--r--packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLWallpaper.java245
-rw-r--r--packages/SystemUI/src/com/android/systemui/glwallpaper/ImageProcessHelper.java144
-rw-r--r--packages/SystemUI/src/com/android/systemui/glwallpaper/ImageRevealHelper.java103
-rw-r--r--packages/SystemUI/src/com/android/systemui/glwallpaper/ImageWallpaperRenderer.java153
-rw-r--r--packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java6
-rw-r--r--packages/SystemUI/src/com/android/systemui/privacy/OngoingPrivacyDialog.kt4
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/tiles/NightDisplayTile.java44
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/NotificationRemoteInputManager.java3
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationClicker.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/AutoTileManager.java18
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java3
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java4
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java17
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarWindowView.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/wallpaper/AodMaskView.java2
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java5
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/AutoTileManagerTest.java14
-rw-r--r--packages/overlays/Android.mk22
-rw-r--r--services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java11
-rw-r--r--services/autofill/java/com/android/server/autofill/Session.java2
-rw-r--r--services/backup/java/com/android/server/backup/encryption/chunking/ByteRange.java80
-rw-r--r--services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptBackupWriter.java75
-rw-r--r--services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptWriter.java36
-rw-r--r--services/backup/java/com/android/server/backup/encryption/chunking/OutputStreamWrapper.java25
-rw-r--r--services/backup/java/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriter.java130
-rw-r--r--services/contentcapture/java/com/android/server/contentcapture/ContentCaptureManagerServiceShellCommand.java27
-rw-r--r--services/core/java/com/android/server/ConnectivityService.java66
-rw-r--r--services/core/java/com/android/server/LocationManagerService.java204
-rw-r--r--services/core/java/com/android/server/am/CoreSettingsObserver.java2
-rw-r--r--services/core/java/com/android/server/audio/AudioDeviceBroker.java63
-rw-r--r--services/core/java/com/android/server/audio/AudioDeviceInventory.java2
-rw-r--r--services/core/java/com/android/server/audio/AudioService.java2
-rw-r--r--services/core/java/com/android/server/audio/BtHelper.java30
-rw-r--r--services/core/java/com/android/server/biometrics/face/FaceService.java1
-rw-r--r--services/core/java/com/android/server/biometrics/fingerprint/FingerprintService.java1
-rw-r--r--services/core/java/com/android/server/display/BrightnessTracker.java16
-rw-r--r--services/core/java/com/android/server/display/ColorDisplayService.java25
-rw-r--r--services/core/java/com/android/server/display/ColorFade.java2
-rw-r--r--services/core/java/com/android/server/display/DisplayTransformManager.java41
-rw-r--r--services/core/java/com/android/server/hdmi/HdmiControlService.java6
-rw-r--r--services/core/java/com/android/server/infra/AbstractMasterSystemService.java40
-rw-r--r--services/core/java/com/android/server/infra/FrameworkResourcesServiceNameResolver.java45
-rw-r--r--services/core/java/com/android/server/infra/ServiceNameResolver.java30
-rw-r--r--services/core/java/com/android/server/location/LocationProviderProxy.java9
-rw-r--r--services/core/java/com/android/server/pm/PackageInstallerSession.java35
-rw-r--r--services/core/java/com/android/server/pm/PackageManagerService.java21
-rw-r--r--services/core/java/com/android/server/pm/dex/DexManager.java7
-rw-r--r--services/core/java/com/android/server/pm/permission/BasePermission.java10
-rw-r--r--services/core/java/com/android/server/pm/permission/PermissionManagerInternal.java5
-rw-r--r--services/core/java/com/android/server/pm/permission/PermissionManagerService.java7
-rw-r--r--services/core/java/com/android/server/policy/PhoneWindowManager.java52
-rw-r--r--services/core/java/com/android/server/policy/WindowManagerPolicy.java4
-rw-r--r--services/core/java/com/android/server/power/Notifier.java49
-rw-r--r--services/core/java/com/android/server/power/PowerManagerService.java93
-rw-r--r--services/core/java/com/android/server/power/batterysaver/BatterySaverPolicy.java5
-rw-r--r--services/core/java/com/android/server/rollback/RollbackManagerServiceImpl.java7
-rw-r--r--services/core/java/com/android/server/wallpaper/WallpaperManagerService.java7
-rw-r--r--services/core/java/com/android/server/wm/ActivityStackSupervisor.java6
-rw-r--r--services/core/java/com/android/server/wm/AppWindowThumbnail.java2
-rw-r--r--services/core/java/com/android/server/wm/AppWindowToken.java2
-rw-r--r--services/core/java/com/android/server/wm/BlackFrame.java2
-rw-r--r--services/core/java/com/android/server/wm/Dimmer.java4
-rw-r--r--services/core/java/com/android/server/wm/DisplayContent.java8
-rw-r--r--services/core/java/com/android/server/wm/Letterbox.java12
-rw-r--r--services/core/java/com/android/server/wm/ScreenRotationAnimation.java2
-rw-r--r--services/core/java/com/android/server/wm/SurfaceAnimator.java2
-rw-r--r--services/core/java/com/android/server/wm/TaskStack.java2
-rw-r--r--services/core/java/com/android/server/wm/WindowContainer.java2
-rw-r--r--services/core/java/com/android/server/wm/WindowState.java9
-rw-r--r--services/core/java/com/android/server/wm/WindowSurfaceController.java2
-rw-r--r--services/robotests/src/com/android/server/backup/encryption/chunking/ByteRangeTest.java57
-rw-r--r--services/robotests/src/com/android/server/backup/encryption/chunking/DiffScriptBackupWriterTest.java90
-rw-r--r--services/robotests/src/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriterTest.java128
-rw-r--r--services/tests/servicestests/src/com/android/server/display/BrightnessTrackerTest.java4
-rw-r--r--services/tests/servicestests/src/com/android/server/display/ColorDisplayServiceTest.java35
-rw-r--r--services/tests/servicestests/src/com/android/server/pm/PackageParserTest.java2
-rw-r--r--services/tests/servicestests/src/com/android/server/pm/dex/DexManagerTests.java7
-rw-r--r--services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java7
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/ActivityMetricsLaunchObserverTests.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/AppChangeTransitionTests.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/AppWindowTokenAnimationTests.java8
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/DimmerTests.java8
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/InsetsSourceProviderTest.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/PendingRemoteAnimationRegistryTest.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/PersisterQueueTests.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/SafeActivityOptionsTest.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/SurfaceAnimatorTest.java15
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/TaskPersisterTest.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/TestWindowManagerPolicy.java5
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/WindowContainerControllerTests.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/WindowStateTests.java35
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/WindowTokenTests.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/WindowTracingTest.java1
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/utils/RotationCacheTest.java1
-rw-r--r--services/usage/java/com/android/server/usage/UsageStatsService.java2
-rw-r--r--startop/view_compiler/OWNERS2
-rw-r--r--telephony/java/com/android/internal/telephony/cdma/SmsMessage.java8
-rw-r--r--tests/RollbackTest/src/com/android/tests/rollback/RollbackTest.java9
-rw-r--r--tools/stats_log_api_gen/Collation.cpp7
-rw-r--r--tools/stats_log_api_gen/Collation.h2
-rw-r--r--tools/stats_log_api_gen/main.cpp16
-rw-r--r--tools/stats_log_api_gen/test.proto18
-rw-r--r--tools/stats_log_api_gen/test_collation.cpp20
218 files changed, 4144 insertions, 3037 deletions
diff --git a/Android.mk b/Android.mk
index 65d4d240fdcd..9c65948f4838 100644
--- a/Android.mk
+++ b/Android.mk
@@ -79,34 +79,6 @@ update-api: doc-comment-check-docs
# ==== hiddenapi lists =======================================
ifneq ($(UNSAFE_DISABLE_HIDDENAPI_FLAGS),true)
-.KATI_RESTAT: $(INTERNAL_PLATFORM_HIDDENAPI_FLAGS)
-$(INTERNAL_PLATFORM_HIDDENAPI_FLAGS): \
- PRIVATE_FLAGS_INPUTS := $(PRIVATE_FLAGS_INPUTS) $(SOONG_HIDDENAPI_FLAGS)
-$(INTERNAL_PLATFORM_HIDDENAPI_FLAGS): \
- frameworks/base/tools/hiddenapi/generate_hiddenapi_lists.py \
- frameworks/base/config/hiddenapi-greylist.txt \
- frameworks/base/config/hiddenapi-greylist-max-p.txt \
- frameworks/base/config/hiddenapi-greylist-max-o.txt \
- frameworks/base/config/hiddenapi-force-blacklist.txt \
- $(INTERNAL_PLATFORM_HIDDENAPI_STUB_FLAGS) \
- $(INTERNAL_PLATFORM_REMOVED_DEX_API_FILE) \
- $(SOONG_HIDDENAPI_FLAGS)
- frameworks/base/tools/hiddenapi/generate_hiddenapi_lists.py \
- --csv $(INTERNAL_PLATFORM_HIDDENAPI_STUB_FLAGS) $(PRIVATE_FLAGS_INPUTS) \
- --greylist frameworks/base/config/hiddenapi-greylist.txt \
- --greylist-ignore-conflicts $(INTERNAL_PLATFORM_REMOVED_DEX_API_FILE) \
- --greylist-max-p frameworks/base/config/hiddenapi-greylist-max-p.txt \
- --greylist-max-o-ignore-conflicts \
- frameworks/base/config/hiddenapi-greylist-max-o.txt \
- --blacklist frameworks/base/config/hiddenapi-force-blacklist.txt \
- --output $@.tmp
- $(call commit-change-for-toc,$@)
-
-$(INTERNAL_PLATFORM_HIDDENAPI_GREYLIST_METADATA): \
- frameworks/base/tools/hiddenapi/merge_csv.py \
- $(PRIVATE_METADATA_INPUTS)
- frameworks/base/tools/hiddenapi/merge_csv.py $(PRIVATE_METADATA_INPUTS) > $@
-
$(call dist-for-goals,droidcore,$(INTERNAL_PLATFORM_HIDDENAPI_FLAGS))
$(call dist-for-goals,droidcore,$(INTERNAL_PLATFORM_HIDDENAPI_GREYLIST_METADATA))
endif # UNSAFE_DISABLE_HIDDENAPI_FLAGS
diff --git a/api/current.txt b/api/current.txt
index 8458ed33ad5d..d6f0955dbca9 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -224,6 +224,11 @@ package android {
public static final class R.attr {
ctor public R.attr();
+ field public static final int __removed1 = 16844185; // 0x1010599
+ field public static final int __removed2 = 16844186; // 0x101059a
+ field public static final int __removed3 = 16844187; // 0x101059b
+ field public static final int __removed4 = 16844188; // 0x101059c
+ field public static final int __removed5 = 16844189; // 0x101059d
field public static final int absListViewStyle = 16842858; // 0x101006a
field public static final int accessibilityEventTypes = 16843648; // 0x1010380
field public static final int accessibilityFeedbackType = 16843650; // 0x1010382
@@ -484,10 +489,6 @@ package android {
field public static final int dashGap = 16843175; // 0x10101a7
field public static final int dashWidth = 16843174; // 0x10101a6
field public static final int data = 16842798; // 0x101002e
- field public static final int dataRetentionTime = 16844189; // 0x101059d
- field public static final int dataSentOffDevice = 16844186; // 0x101059a
- field public static final int dataSharedWithThirdParty = 16844187; // 0x101059b
- field public static final int dataUsedForMonetization = 16844188; // 0x101059c
field public static final int datePickerDialogTheme = 16843948; // 0x10104ac
field public static final int datePickerMode = 16843955; // 0x10104b3
field public static final int datePickerStyle = 16843612; // 0x101035c
@@ -1508,7 +1509,6 @@ package android {
field @Deprecated public static final int unfocusedMonthDateColor = 16843588; // 0x1010344
field public static final int unselectedAlpha = 16843278; // 0x101020e
field public static final int updatePeriodMillis = 16843344; // 0x1010250
- field public static final int usageInfoRequired = 16844185; // 0x1010599
field public static final int use32bitAbi = 16844053; // 0x1010515
field public static final int useAppZygote = 16844184; // 0x1010598
field public static final int useDefaultMargins = 16843641; // 0x1010379
@@ -10265,7 +10265,6 @@ package android.content {
field public static final String ACTION_PACKAGE_RESTARTED = "android.intent.action.PACKAGE_RESTARTED";
field public static final String ACTION_PACKAGE_VERIFIED = "android.intent.action.PACKAGE_VERIFIED";
field public static final String ACTION_PASTE = "android.intent.action.PASTE";
- field public static final String ACTION_PERMISSION_USAGE_DETAILS = "android.intent.action.PERMISSION_USAGE_DETAILS";
field public static final String ACTION_PICK = "android.intent.action.PICK";
field public static final String ACTION_PICK_ACTIVITY = "android.intent.action.PICK_ACTIVITY";
field public static final String ACTION_POWER_CONNECTED = "android.intent.action.ACTION_POWER_CONNECTED";
@@ -10391,7 +10390,6 @@ package android.content {
field public static final String EXTRA_NOT_UNKNOWN_SOURCE = "android.intent.extra.NOT_UNKNOWN_SOURCE";
field public static final String EXTRA_ORIGINATING_URI = "android.intent.extra.ORIGINATING_URI";
field public static final String EXTRA_PACKAGE_NAME = "android.intent.extra.PACKAGE_NAME";
- field public static final String EXTRA_PERMISSION_USAGE_PERMISSIONS = "android.intent.extra.PERMISSION_USAGE_PERMISSIONS";
field public static final String EXTRA_PHONE_NUMBER = "android.intent.extra.PHONE_NUMBER";
field public static final String EXTRA_PROCESS_TEXT = "android.intent.extra.PROCESS_TEXT";
field public static final String EXTRA_PROCESS_TEXT_READONLY = "android.intent.extra.PROCESS_TEXT_READONLY";
@@ -11356,8 +11354,8 @@ package android.content.pm {
field public android.content.pm.ProviderInfo[] providers;
field public android.content.pm.ActivityInfo[] receivers;
field public android.content.pm.FeatureInfo[] reqFeatures;
- field @Deprecated public String[] requestedPermissions;
- field @Deprecated public int[] requestedPermissionsFlags;
+ field public String[] requestedPermissions;
+ field public int[] requestedPermissionsFlags;
field public android.content.pm.ServiceInfo[] services;
field public String sharedUserId;
field public int sharedUserLabel;
@@ -11365,7 +11363,6 @@ package android.content.pm {
field public android.content.pm.SigningInfo signingInfo;
field public String[] splitNames;
field public int[] splitRevisionCodes;
- field public android.content.pm.UsesPermissionInfo[] usesPermissions;
field @Deprecated public int versionCode;
field public String versionName;
}
@@ -11865,7 +11862,6 @@ package android.content.pm {
field public String group;
field public CharSequence nonLocalizedDescription;
field @Deprecated public int protectionLevel;
- field public boolean usageInfoRequired;
}
public final class ProviderInfo extends android.content.pm.ComponentInfo implements android.os.Parcelable {
@@ -12057,28 +12053,6 @@ package android.content.pm {
field public static final android.os.Parcelable.Creator<android.content.pm.SigningInfo> CREATOR;
}
- public final class UsesPermissionInfo extends android.content.pm.PackageItemInfo implements android.os.Parcelable {
- method public int describeContents();
- method public int getDataRetention();
- method public int getDataRetentionWeeks();
- method public int getDataSentOffDevice();
- method public int getDataSharedWithThirdParty();
- method public int getDataUsedForMonetization();
- method public int getFlags();
- method public String getPermission();
- field public static final android.os.Parcelable.Creator<android.content.pm.UsesPermissionInfo> CREATOR;
- field public static final int FLAG_REQUESTED_PERMISSION_GRANTED = 2; // 0x2
- field public static final int RETENTION_NOT_RETAINED = 1; // 0x1
- field public static final int RETENTION_SPECIFIED = 4; // 0x4
- field public static final int RETENTION_UNDEFINED = 0; // 0x0
- field public static final int RETENTION_UNLIMITED = 3; // 0x3
- field public static final int RETENTION_USER_SELECTED = 2; // 0x2
- field public static final int USAGE_NO = 3; // 0x3
- field public static final int USAGE_UNDEFINED = 0; // 0x0
- field public static final int USAGE_USER_TRIGGERED = 2; // 0x2
- field public static final int USAGE_YES = 1; // 0x1
- }
-
public final class VersionedPackage implements android.os.Parcelable {
ctor public VersionedPackage(@NonNull String, int);
ctor public VersionedPackage(@NonNull String, long);
@@ -12356,8 +12330,10 @@ package android.content.res {
public final class Resources.Theme {
method public void applyStyle(int, boolean);
method public void dump(int, String, String);
+ method public int[] getAttributeResolutionStack(@AttrRes int, @StyleRes int, @StyleRes int);
method public int getChangingConfigurations();
method public android.graphics.drawable.Drawable getDrawable(@DrawableRes int) throws android.content.res.Resources.NotFoundException;
+ method @StyleRes public int getExplicitStyle(@Nullable android.util.AttributeSet);
method public android.content.res.Resources getResources();
method @NonNull public android.content.res.TypedArray obtainStyledAttributes(@NonNull @StyleableRes int[]);
method @NonNull public android.content.res.TypedArray obtainStyledAttributes(@StyleRes int, @NonNull @StyleableRes int[]) throws android.content.res.Resources.NotFoundException;
@@ -14196,6 +14172,7 @@ package android.graphics {
field public static final int DEPTH_POINT_CLOUD = 257; // 0x101
field public static final int FLEX_RGBA_8888 = 42; // 0x2a
field public static final int FLEX_RGB_888 = 41; // 0x29
+ field public static final int HEIC = 1212500294; // 0x48454946
field public static final int JPEG = 256; // 0x100
field public static final int NV16 = 16; // 0x10
field public static final int NV21 = 17; // 0x11
@@ -19446,9 +19423,9 @@ package android.icu.text {
method public static android.icu.text.BreakIterator getSentenceInstance(java.util.Locale);
method public static android.icu.text.BreakIterator getSentenceInstance(android.icu.util.ULocale);
method public abstract java.text.CharacterIterator getText();
- method public static android.icu.text.BreakIterator getTitleInstance();
- method public static android.icu.text.BreakIterator getTitleInstance(java.util.Locale);
- method public static android.icu.text.BreakIterator getTitleInstance(android.icu.util.ULocale);
+ method @Deprecated public static android.icu.text.BreakIterator getTitleInstance();
+ method @Deprecated public static android.icu.text.BreakIterator getTitleInstance(java.util.Locale);
+ method @Deprecated public static android.icu.text.BreakIterator getTitleInstance(android.icu.util.ULocale);
method public static android.icu.text.BreakIterator getWordInstance();
method public static android.icu.text.BreakIterator getWordInstance(java.util.Locale);
method public static android.icu.text.BreakIterator getWordInstance(android.icu.util.ULocale);
@@ -19465,7 +19442,7 @@ package android.icu.text {
field public static final int KIND_CHARACTER = 0; // 0x0
field public static final int KIND_LINE = 2; // 0x2
field public static final int KIND_SENTENCE = 3; // 0x3
- field public static final int KIND_TITLE = 4; // 0x4
+ field @Deprecated public static final int KIND_TITLE = 4; // 0x4
field public static final int KIND_WORD = 1; // 0x1
field public static final int WORD_IDEO = 400; // 0x190
field public static final int WORD_IDEO_LIMIT = 500; // 0x1f4
@@ -22643,6 +22620,7 @@ package android.location {
method public int getCodeType();
method public int getConstellationType();
method public int getMultipathIndicator();
+ method @NonNull public String getOtherCodeTypeName();
method public double getPseudorangeRateMetersPerSecond();
method public double getPseudorangeRateUncertaintyMetersPerSecond();
method public long getReceivedSvTimeNanos();
@@ -22668,10 +22646,11 @@ package android.location {
field public static final int CODE_TYPE_A = 0; // 0x0
field public static final int CODE_TYPE_B = 1; // 0x1
field public static final int CODE_TYPE_C = 2; // 0x2
- field public static final int CODE_TYPE_CODELESS = 13; // 0xd
field public static final int CODE_TYPE_I = 3; // 0x3
field public static final int CODE_TYPE_L = 4; // 0x4
field public static final int CODE_TYPE_M = 5; // 0x5
+ field public static final int CODE_TYPE_N = 13; // 0xd
+ field public static final int CODE_TYPE_OTHER = 255; // 0xff
field public static final int CODE_TYPE_P = 6; // 0x6
field public static final int CODE_TYPE_Q = 7; // 0x7
field public static final int CODE_TYPE_S = 8; // 0x8
@@ -50327,6 +50306,8 @@ package android.view {
method @android.view.ViewDebug.ExportedProperty(category="drawing") public float getAlpha();
method public android.view.animation.Animation getAnimation();
method public android.os.IBinder getApplicationWindowToken();
+ method @NonNull public java.util.List<java.lang.Integer> getAttributeResolutionStack();
+ method @NonNull public java.util.Map<java.lang.Integer,java.lang.Integer> getAttributeSourceResourceMap();
method @android.view.ViewDebug.ExportedProperty @Nullable public String[] getAutofillHints();
method public final android.view.autofill.AutofillId getAutofillId();
method public int getAutofillType();
@@ -50357,6 +50338,7 @@ package android.view {
method public void getDrawingRect(android.graphics.Rect);
method public long getDrawingTime();
method @android.view.ViewDebug.ExportedProperty(category="drawing") public float getElevation();
+ method @StyleRes public int getExplicitStyle();
method @android.view.ViewDebug.ExportedProperty public boolean getFilterTouchesWhenObscured();
method @android.view.ViewDebug.ExportedProperty public boolean getFitsSystemWindows();
method @android.view.ViewDebug.ExportedProperty(mapping={@android.view.ViewDebug.IntToString(from=android.view.View.NOT_FOCUSABLE, to="NOT_FOCUSABLE"), @android.view.ViewDebug.IntToString(from=android.view.View.FOCUSABLE, to="FOCUSABLE"), @android.view.ViewDebug.IntToString(from=android.view.View.FOCUSABLE_AUTO, to="FOCUSABLE_AUTO")}, category="focus") public int getFocusable();
@@ -50651,6 +50633,7 @@ package android.view {
method public static int resolveSizeAndState(int, int, int);
method public boolean restoreDefaultFocus();
method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>);
+ method public final void saveAttributeDataForStyleable(@NonNull android.content.Context, @NonNull int[], @Nullable android.util.AttributeSet, @NonNull android.content.res.TypedArray, int, int);
method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>);
method public void scheduleDrawable(@NonNull android.graphics.drawable.Drawable, @NonNull Runnable, long);
method public void scrollBy(int, int);
diff --git a/api/removed.txt b/api/removed.txt
index 9f4b0416246d..262ffec46de1 100644
--- a/api/removed.txt
+++ b/api/removed.txt
@@ -344,7 +344,7 @@ package android.os {
public final class PowerManager {
method public void goToSleep(long);
method @Deprecated public void userActivity(long, boolean);
- method public void wakeUp(long);
+ method @Deprecated public void wakeUp(long);
}
public class RecoverySystem {
diff --git a/api/system-current.txt b/api/system-current.txt
index 8ac5f534cab2..b7fc33950642 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -3920,6 +3920,7 @@ package android.net {
method @RequiresPermission(android.Manifest.permission.TETHER_PRIVILEGED) public void getLatestTetheringEntitlementValue(int, boolean, @NonNull android.net.ConnectivityManager.TetheringEntitlementValueListener, @Nullable android.os.Handler);
method @RequiresPermission(anyOf={android.Manifest.permission.TETHER_PRIVILEGED, android.Manifest.permission.WRITE_SETTINGS}) public boolean isTetheringSupported();
method @RequiresPermission(anyOf={"android.permission.NETWORK_SETTINGS", android.Manifest.permission.NETWORK_SETUP_WIZARD, "android.permission.NETWORK_STACK"}) public void setAirplaneMode(boolean);
+ method @RequiresPermission(android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) public void startCaptivePortalApp(android.os.Bundle);
method @RequiresPermission(android.Manifest.permission.TETHER_PRIVILEGED) public void startTethering(int, boolean, android.net.ConnectivityManager.OnStartTetheringCallback);
method @RequiresPermission(android.Manifest.permission.TETHER_PRIVILEGED) public void startTethering(int, boolean, android.net.ConnectivityManager.OnStartTetheringCallback, android.os.Handler);
method @RequiresPermission(android.Manifest.permission.TETHER_PRIVILEGED) public void stopTethering(int);
@@ -5002,10 +5003,11 @@ package android.os {
method public boolean getEnableAdjustBrightness();
method public boolean getEnableDataSaver();
method public boolean getEnableFirewall();
+ method public boolean getEnableNightMode();
method public boolean getEnableQuickDoze();
method public boolean getForceAllAppsStandby();
method public boolean getForceBackgroundCheck();
- method public int getGpsMode();
+ method public int getLocationMode();
method public void writeToParcel(android.os.Parcel, int);
field public static final android.os.Parcelable.Creator<android.os.BatterySaverPolicyConfig> CREATOR;
}
@@ -5027,10 +5029,11 @@ package android.os {
method @NonNull public android.os.BatterySaverPolicyConfig.Builder setEnableAdjustBrightness(boolean);
method @NonNull public android.os.BatterySaverPolicyConfig.Builder setEnableDataSaver(boolean);
method @NonNull public android.os.BatterySaverPolicyConfig.Builder setEnableFirewall(boolean);
+ method @NonNull public android.os.BatterySaverPolicyConfig.Builder setEnableNightMode(boolean);
method @NonNull public android.os.BatterySaverPolicyConfig.Builder setEnableQuickDoze(boolean);
method @NonNull public android.os.BatterySaverPolicyConfig.Builder setForceAllAppsStandby(boolean);
method @NonNull public android.os.BatterySaverPolicyConfig.Builder setForceBackgroundCheck(boolean);
- method @NonNull public android.os.BatterySaverPolicyConfig.Builder setGpsMode(int);
+ method @NonNull public android.os.BatterySaverPolicyConfig.Builder setLocationMode(int);
}
public class Binder implements android.os.IBinder {
diff --git a/api/test-current.txt b/api/test-current.txt
index 5b51d6e42a68..2c8d08c49fdb 100644
--- a/api/test-current.txt
+++ b/api/test-current.txt
@@ -767,6 +767,7 @@ package android.location {
method public void setCodeType(int);
method public void setConstellationType(int);
method public void setMultipathIndicator(int);
+ method public void setOtherCodeTypeName(@NonNull String);
method public void setPseudorangeRateMetersPerSecond(double);
method public void setPseudorangeRateUncertaintyMetersPerSecond(double);
method public void setReceivedSvTimeNanos(long);
@@ -934,6 +935,7 @@ package android.net {
}
public class ConnectivityManager {
+ method @RequiresPermission(android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) public void startCaptivePortalApp(android.os.Bundle);
field public static final String EXTRA_CAPTIVE_PORTAL_PROBE_SPEC = "android.net.extra.CAPTIVE_PORTAL_PROBE_SPEC";
field public static final String EXTRA_CAPTIVE_PORTAL_USER_AGENT = "android.net.extra.CAPTIVE_PORTAL_USER_AGENT";
}
@@ -2578,6 +2580,10 @@ package android.view {
method public void setDisplayId(int);
}
+ @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.RUNTIME) @java.lang.annotation.Target({java.lang.annotation.ElementType.METHOD}) public @interface RemotableViewMethod {
+ method public abstract String asyncImpl() default "";
+ }
+
@UiThread public class View implements android.view.accessibility.AccessibilityEventSource android.graphics.drawable.Drawable.Callback android.view.KeyEvent.Callback {
method public android.view.View getTooltipView();
method public static boolean isDefaultFocusHighlightEnabled();
@@ -2664,6 +2670,8 @@ package android.view.autofill {
public final class AutofillId implements android.os.Parcelable {
ctor public AutofillId(int);
ctor public AutofillId(@NonNull android.view.autofill.AutofillId, int);
+ ctor public AutofillId(int, int);
+ ctor public AutofillId(@NonNull android.view.autofill.AutofillId, long, int);
}
public final class AutofillManager {
@@ -2713,6 +2721,66 @@ package android.view.contentcapture {
public final class ViewNode extends android.app.assist.AssistStructure.ViewNode {
method @Nullable public android.view.autofill.AutofillId getParentAutofillId();
+ method @Nullable public static android.view.contentcapture.ViewNode readFromParcel(@NonNull android.os.Parcel);
+ method public static void writeToParcel(@NonNull android.os.Parcel, @Nullable android.view.contentcapture.ViewNode, int);
+ }
+
+ public static final class ViewNode.ViewStructureImpl extends android.view.ViewStructure {
+ ctor public ViewNode.ViewStructureImpl(@NonNull android.view.View);
+ ctor public ViewNode.ViewStructureImpl(@NonNull android.view.autofill.AutofillId, long, int);
+ method public int addChildCount(int);
+ method public void asyncCommit();
+ method public android.view.ViewStructure asyncNewChild(int);
+ method public android.view.autofill.AutofillId getAutofillId();
+ method public int getChildCount();
+ method public android.os.Bundle getExtras();
+ method public CharSequence getHint();
+ method public android.view.contentcapture.ViewNode getNode();
+ method public android.graphics.Rect getTempRect();
+ method public CharSequence getText();
+ method public int getTextSelectionEnd();
+ method public int getTextSelectionStart();
+ method public boolean hasExtras();
+ method public android.view.ViewStructure newChild(int);
+ method public android.view.ViewStructure.HtmlInfo.Builder newHtmlInfoBuilder(String);
+ method public void setAccessibilityFocused(boolean);
+ method public void setActivated(boolean);
+ method public void setAlpha(float);
+ method public void setAssistBlocked(boolean);
+ method public void setAutofillHints(String[]);
+ method public void setAutofillId(android.view.autofill.AutofillId);
+ method public void setAutofillId(android.view.autofill.AutofillId, int);
+ method public void setAutofillOptions(CharSequence[]);
+ method public void setAutofillType(int);
+ method public void setAutofillValue(android.view.autofill.AutofillValue);
+ method public void setCheckable(boolean);
+ method public void setChecked(boolean);
+ method public void setChildCount(int);
+ method public void setClassName(String);
+ method public void setClickable(boolean);
+ method public void setContentDescription(CharSequence);
+ method public void setContextClickable(boolean);
+ method public void setDataIsSensitive(boolean);
+ method public void setDimens(int, int, int, int, int, int);
+ method public void setElevation(float);
+ method public void setEnabled(boolean);
+ method public void setFocusable(boolean);
+ method public void setFocused(boolean);
+ method public void setHint(CharSequence);
+ method public void setHtmlInfo(android.view.ViewStructure.HtmlInfo);
+ method public void setId(int, String, String, String);
+ method public void setInputType(int);
+ method public void setLocaleList(android.os.LocaleList);
+ method public void setLongClickable(boolean);
+ method public void setOpaque(boolean);
+ method public void setSelected(boolean);
+ method public void setText(CharSequence);
+ method public void setText(CharSequence, int, int);
+ method public void setTextLines(int[], int[]);
+ method public void setTextStyle(float, int, int, int);
+ method public void setTransformation(android.graphics.Matrix);
+ method public void setVisibility(int);
+ method public void setWebDomain(String);
}
}
diff --git a/cmds/idmap2/Android.bp b/cmds/idmap2/Android.bp
index 056add5c71b5..2fef407a8e3f 100644
--- a/cmds/idmap2/Android.bp
+++ b/cmds/idmap2/Android.bp
@@ -43,6 +43,7 @@ cc_library {
"libidmap2/PrettyPrintVisitor.cpp",
"libidmap2/RawPrintVisitor.cpp",
"libidmap2/ResourceUtils.cpp",
+ "libidmap2/Result.cpp",
"libidmap2/Xml.cpp",
"libidmap2/ZipFile.cpp",
],
@@ -93,6 +94,7 @@ cc_test {
"tests/PrettyPrintVisitorTests.cpp",
"tests/RawPrintVisitorTests.cpp",
"tests/ResourceUtilsTests.cpp",
+ "tests/ResultTests.cpp",
"tests/XmlTests.cpp",
"tests/ZipFileTests.cpp",
],
diff --git a/cmds/idmap2/include/idmap2/Result.h b/cmds/idmap2/include/idmap2/Result.h
index 6189ea371ee1..d88dd5179610 100644
--- a/cmds/idmap2/include/idmap2/Result.h
+++ b/cmds/idmap2/include/idmap2/Result.h
@@ -18,6 +18,11 @@
#define IDMAP2_INCLUDE_IDMAP2_RESULT_H_
#include <optional>
+#include <string>
+#include <utility>
+#include <variant>
+
+#include "android-base/logging.h" // CHECK
namespace android::idmap2 {
@@ -26,6 +31,125 @@ using Result = std::optional<T>;
static constexpr std::nullopt_t kResultError = std::nullopt;
+namespace v2 {
+
+using Unit = std::monostate;
+
+class Error {
+ public:
+ explicit Error(const Error& parent) = default;
+
+ // NOLINTNEXTLINE(cert-dcl50-cpp)
+ explicit Error(const char* fmt, ...) __attribute__((__format__(printf, 2, 3)));
+
+ // NOLINTNEXTLINE(cert-dcl50-cpp)
+ explicit Error(const Error& parent, const char* fmt, ...)
+ __attribute__((__format__(printf, 3, 4)));
+
+ inline std::string GetMessage() const {
+ return msg_;
+ }
+
+ private:
+ std::string msg_;
+};
+
+template <typename T>
+class Result {
+ public:
+ Result(const T& value); // NOLINT(runtime/explicit)
+ Result(T&& value) noexcept; // NOLINT(runtime/explicit)
+
+ Result(const Error& error); // NOLINT(runtime/explicit)
+ Result(Error&& error) noexcept; // NOLINT(runtime/explicit)
+
+ Result(const Result& error) = default;
+
+ Result& operator=(const Result& rhs) = default;
+ Result& operator=(Result&& rhs) noexcept = default;
+
+ explicit operator bool() const;
+
+ constexpr const T& operator*() const&;
+ T& operator*() &;
+
+ constexpr const T* operator->() const&;
+ T* operator->() &;
+
+ std::string GetErrorMessage() const;
+ Error GetError() const;
+
+ private:
+ bool is_ok() const;
+
+ std::variant<T, Error> data_;
+};
+
+template <typename T>
+Result<T>::Result(const T& value) : data_(std::in_place_type<T>, value) {
+}
+
+template <typename T>
+Result<T>::Result(T&& value) noexcept : data_(std::in_place_type<T>, std::forward<T>(value)) {
+}
+
+template <typename T>
+Result<T>::Result(const Error& error) : data_(std::in_place_type<Error>, error) {
+}
+
+template <typename T>
+Result<T>::Result(Error&& error) noexcept
+ : data_(std::in_place_type<Error>, std::forward<Error>(error)) {
+}
+
+template <typename T>
+Result<T>::operator bool() const {
+ return is_ok();
+}
+
+template <typename T>
+constexpr const T& Result<T>::operator*() const& {
+ CHECK(is_ok()) << "Result<T>::operator* called in ERROR state";
+ return std::get<T>(data_);
+}
+
+template <typename T>
+T& Result<T>::operator*() & {
+ CHECK(is_ok()) << "Result<T>::operator* called in ERROR state";
+ return std::get<T>(data_);
+}
+
+template <typename T>
+constexpr const T* Result<T>::operator->() const& {
+ CHECK(is_ok()) << "Result<T>::operator-> called in ERROR state";
+ return &std::get<T>(data_);
+}
+
+template <typename T>
+T* Result<T>::operator->() & {
+ CHECK(is_ok()) << "Result<T>::operator-> called in ERROR state";
+ return &std::get<T>(data_);
+}
+
+template <typename T>
+inline std::string Result<T>::GetErrorMessage() const {
+ CHECK(!is_ok()) << "Result<T>::GetErrorMessage called in OK state";
+ return std::get<Error>(data_).GetMessage();
+}
+
+template <typename T>
+inline Error Result<T>::GetError() const {
+ CHECK(!is_ok()) << "Result<T>::GetError called in OK state";
+ return Error(std::get<Error>(data_));
+}
+
+template <typename T>
+inline bool Result<T>::is_ok() const {
+ return std::holds_alternative<T>(data_);
+}
+
+} // namespace v2
+
} // namespace android::idmap2
#endif // IDMAP2_INCLUDE_IDMAP2_RESULT_H_
diff --git a/cmds/idmap2/libidmap2/Idmap.cpp b/cmds/idmap2/libidmap2/Idmap.cpp
index fa5ac8ea11dc..b19d7a971cb8 100644
--- a/cmds/idmap2/libidmap2/Idmap.cpp
+++ b/cmds/idmap2/libidmap2/Idmap.cpp
@@ -117,6 +117,12 @@ const LoadedPackage* GetPackageAtIndex0(const LoadedArsc& loaded_arsc) {
return loaded_arsc.GetPackageById(id);
}
+Result<uint32_t> GetCrc(const ZipFile& zip) {
+ const Result<uint32_t> a = zip.Crc("resources.arsc");
+ const Result<uint32_t> b = zip.Crc("AndroidManifest.xml");
+ return a && b ? Result<uint32_t>(*a ^ *b) : kResultError;
+}
+
} // namespace
std::unique_ptr<const IdmapHeader> IdmapHeader::FromBinaryStream(std::istream& stream) {
@@ -153,7 +159,7 @@ bool IdmapHeader::IsUpToDate(std::ostream& out_error) const {
return false;
}
- Result<uint32_t> target_crc = target_zip->Crc("resources.arsc");
+ Result<uint32_t> target_crc = GetCrc(*target_zip);
if (!target_crc) {
out_error << "error: failed to get target crc" << std::endl;
return false;
@@ -173,7 +179,7 @@ bool IdmapHeader::IsUpToDate(std::ostream& out_error) const {
return false;
}
- Result<uint32_t> overlay_crc = overlay_zip->Crc("resources.arsc");
+ Result<uint32_t> overlay_crc = GetCrc(*overlay_zip);
if (!overlay_crc) {
out_error << "error: failed to get overlay crc" << std::endl;
return false;
@@ -356,14 +362,14 @@ std::unique_ptr<const Idmap> Idmap::FromApkAssets(
header->magic_ = kIdmapMagic;
header->version_ = kIdmapCurrentVersion;
- Result<uint32_t> crc = target_zip->Crc("resources.arsc");
+ Result<uint32_t> crc = GetCrc(*target_zip);
if (!crc) {
out_error << "error: failed to get zip crc for target" << std::endl;
return nullptr;
}
header->target_crc_ = *crc;
- crc = overlay_zip->Crc("resources.arsc");
+ crc = GetCrc(*overlay_zip);
if (!crc) {
out_error << "error: failed to get zip crc for overlay" << std::endl;
return nullptr;
diff --git a/cmds/idmap2/libidmap2/Result.cpp b/cmds/idmap2/libidmap2/Result.cpp
new file mode 100644
index 000000000000..a5c999916c72
--- /dev/null
+++ b/cmds/idmap2/libidmap2/Result.cpp
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <cstdarg>
+
+#include "android-base/stringprintf.h"
+
+#include "idmap2/Result.h"
+
+namespace android::idmap2 {
+
+v2::Error::Error(const char* fmt, ...) {
+ va_list ap;
+ va_start(ap, fmt);
+ base::StringAppendV(&msg_, fmt, ap);
+ va_end(ap);
+}
+
+v2::Error::Error(const Error& parent, const char* fmt, ...) : msg_(parent.msg_) {
+ msg_.append(" -> ");
+
+ va_list ap;
+ va_start(ap, fmt);
+ base::StringAppendV(&msg_, fmt, ap);
+ va_end(ap);
+}
+
+} // namespace android::idmap2
diff --git a/cmds/idmap2/static-checks.sh b/cmds/idmap2/static-checks.sh
index ad9830b8a096..57407102843b 100755
--- a/cmds/idmap2/static-checks.sh
+++ b/cmds/idmap2/static-checks.sh
@@ -73,6 +73,7 @@ function _cpplint()
local output="$($cpplint --quiet $cpp_files 2>&1 >/dev/null | grep -v \
-e 'Found C system header after C++ system header.' \
-e 'Unknown NOLINT error category: misc-non-private-member-variables-in-classes' \
+ -e 'Unknown NOLINT error category: performance-unnecessary-copy-initialization' \
)"
if [[ "$output" ]]; then
echo "$output"
diff --git a/cmds/idmap2/tests/IdmapTests.cpp b/cmds/idmap2/tests/IdmapTests.cpp
index 9e27ccd7cfbb..b40521f054af 100644
--- a/cmds/idmap2/tests/IdmapTests.cpp
+++ b/cmds/idmap2/tests/IdmapTests.cpp
@@ -191,8 +191,8 @@ TEST(IdmapTests, CreateIdmapFromApkAssets) {
ASSERT_THAT(idmap->GetHeader(), NotNull());
ASSERT_EQ(idmap->GetHeader()->GetMagic(), 0x504d4449U);
ASSERT_EQ(idmap->GetHeader()->GetVersion(), 0x01U);
- ASSERT_EQ(idmap->GetHeader()->GetTargetCrc(), 0xab7cf70d);
- ASSERT_EQ(idmap->GetHeader()->GetOverlayCrc(), 0xd470336b);
+ ASSERT_EQ(idmap->GetHeader()->GetTargetCrc(), 0xdd53ca29);
+ ASSERT_EQ(idmap->GetHeader()->GetOverlayCrc(), 0xa71ccd77);
ASSERT_EQ(idmap->GetHeader()->GetTargetPath().to_string(), target_apk_path);
ASSERT_EQ(idmap->GetHeader()->GetOverlayPath(), overlay_apk_path);
ASSERT_EQ(idmap->GetHeader()->GetOverlayPath(), overlay_apk_path);
diff --git a/cmds/idmap2/tests/RawPrintVisitorTests.cpp b/cmds/idmap2/tests/RawPrintVisitorTests.cpp
index b1ca12557dcb..a5588c330d85 100644
--- a/cmds/idmap2/tests/RawPrintVisitorTests.cpp
+++ b/cmds/idmap2/tests/RawPrintVisitorTests.cpp
@@ -52,8 +52,8 @@ TEST(RawPrintVisitorTests, CreateRawPrintVisitor) {
ASSERT_NE(stream.str().find("00000000: 504d4449 magic\n"), std::string::npos);
ASSERT_NE(stream.str().find("00000004: 00000001 version\n"), std::string::npos);
- ASSERT_NE(stream.str().find("00000008: ab7cf70d target crc\n"), std::string::npos);
- ASSERT_NE(stream.str().find("0000000c: d470336b overlay crc\n"), std::string::npos);
+ ASSERT_NE(stream.str().find("00000008: dd53ca29 target crc\n"), std::string::npos);
+ ASSERT_NE(stream.str().find("0000000c: a71ccd77 overlay crc\n"), std::string::npos);
ASSERT_NE(stream.str().find("0000021c: 00000000 0x7f010000 -> 0x7f010000 integer/int1\n"),
std::string::npos);
}
diff --git a/cmds/idmap2/tests/ResultTests.cpp b/cmds/idmap2/tests/ResultTests.cpp
new file mode 100644
index 000000000000..d82f0c475ea9
--- /dev/null
+++ b/cmds/idmap2/tests/ResultTests.cpp
@@ -0,0 +1,288 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <memory>
+#include <type_traits>
+#include <utility>
+
+#include "gmock/gmock.h"
+#include "gtest/gtest.h"
+
+#include "idmap2/Result.h"
+
+namespace android::idmap2 {
+
+struct Container {
+ uint32_t value; // NOLINT(misc-non-private-member-variables-in-classes)
+};
+
+// Tests: Error
+
+TEST(ResultTests, ErrorTraits) {
+ ASSERT_TRUE(std::is_move_constructible<v2::Error>::value);
+ ASSERT_TRUE(std::is_move_assignable<v2::Error>::value);
+ ASSERT_TRUE(std::is_copy_constructible<v2::Error>::value);
+ ASSERT_TRUE(std::is_copy_assignable<v2::Error>::value);
+}
+
+TEST(ResultTests, ErrorCtorFormat) {
+ v2::Error e("%s=0x%08x", "resid", 0x7f010002);
+ ASSERT_EQ(e.GetMessage(), "resid=0x7f010002");
+}
+
+TEST(ResultTests, ErrorPropagateParent) {
+ v2::Error e1("foo");
+ ASSERT_EQ(e1.GetMessage(), "foo");
+
+ v2::Error e2(e1, "bar");
+ ASSERT_EQ(e2.GetMessage(), "foo -> bar");
+
+ v2::Error e3(e2); // NOLINT(performance-unnecessary-copy-initialization)
+ ASSERT_EQ(e3.GetMessage(), "foo -> bar");
+
+ v2::Error e4(e3, "%02d", 1);
+ ASSERT_EQ(e4.GetMessage(), "foo -> bar -> 01");
+}
+
+// Tests: Result<T> member functions
+
+// Result(const Result&)
+TEST(ResultTests, CopyConstructor) {
+ v2::Result<uint32_t> r1(42U);
+
+ v2::Result<uint32_t> r2(r1);
+ ASSERT_TRUE(r2);
+ ASSERT_EQ(*r2, 42U);
+
+ v2::Result<uint32_t> r3 = r2;
+ ASSERT_TRUE(r3);
+ ASSERT_EQ(*r3, 42U);
+}
+
+// Result(const T&)
+TEST(ResultTests, Constructor) {
+ uint32_t v = 42U;
+ v2::Result<uint32_t> r1(v);
+ ASSERT_TRUE(r1);
+ ASSERT_EQ(*r1, 42U);
+
+ v2::Error e("foo");
+ v2::Result<uint32_t> r2(e);
+ ASSERT_FALSE(r2);
+ ASSERT_EQ(r2.GetErrorMessage(), "foo");
+}
+
+// Result(const T&&)
+TEST(ResultTests, MoveConstructor) {
+ v2::Result<uint32_t> r1(42U);
+ ASSERT_TRUE(r1);
+ ASSERT_EQ(*r1, 42U);
+
+ v2::Result<uint32_t> r2(v2::Error("foo"));
+ ASSERT_FALSE(r2);
+ ASSERT_EQ(r2.GetErrorMessage(), "foo");
+}
+
+// operator=
+TEST(ResultTests, CopyAssignmentOperator) {
+ // note: 'Result<...> r2 = r1;' calls the copy ctor
+ v2::Result<uint32_t> r1(42U);
+ v2::Result<uint32_t> r2(0U);
+ r2 = r1;
+ ASSERT_TRUE(r2);
+ ASSERT_EQ(*r2, 42U);
+
+ v2::Result<uint32_t> r3(v2::Error("foo"));
+ r2 = r3;
+ ASSERT_FALSE(r2);
+ ASSERT_EQ(r2.GetErrorMessage(), "foo");
+}
+
+TEST(ResultTests, MoveAssignmentOperator) {
+ v2::Result<uint32_t> r(0U);
+ r = v2::Result<uint32_t>(42U);
+ ASSERT_TRUE(r);
+ ASSERT_EQ(*r, 42U);
+
+ r = v2::Result<uint32_t>(v2::Error("foo"));
+ ASSERT_FALSE(r);
+ ASSERT_EQ(r.GetErrorMessage(), "foo");
+}
+
+// operator bool()
+TEST(ResultTests, BoolOperator) {
+ v2::Result<uint32_t> r1(42U);
+ ASSERT_TRUE(r1);
+ ASSERT_EQ(*r1, 42U);
+
+ v2::Result<uint32_t> r2(v2::Error("foo"));
+ ASSERT_FALSE(r2);
+ ASSERT_EQ(r2.GetErrorMessage(), "foo");
+}
+
+// operator*
+TEST(ResultTests, IndirectionOperator) {
+ const v2::Result<uint32_t> r1(42U);
+ ASSERT_TRUE(r1);
+ ASSERT_EQ(*r1, 42U);
+
+ const v2::Result<Container> r2(Container{42U});
+ ASSERT_TRUE(r2);
+ const Container& c = *r2;
+ ASSERT_EQ(c.value, 42U);
+
+ v2::Result<Container> r3(Container{42U});
+ ASSERT_TRUE(r3);
+ ASSERT_EQ((*r3).value, 42U);
+ (*r3).value = 0U;
+ ASSERT_EQ((*r3).value, 0U);
+}
+
+// operator->
+TEST(ResultTests, DereferenceOperator) {
+ const v2::Result<Container> r1(Container{42U});
+ ASSERT_TRUE(r1);
+ ASSERT_EQ(r1->value, 42U);
+
+ v2::Result<Container> r2(Container{42U});
+ ASSERT_TRUE(r2);
+ ASSERT_EQ(r2->value, 42U);
+ r2->value = 0U;
+ ASSERT_EQ(r2->value, 0U);
+}
+
+// Tests: intended use of Result<T>
+
+TEST(ResultTests, ResultTraits) {
+ ASSERT_TRUE(std::is_move_constructible<v2::Result<uint32_t>>::value);
+ ASSERT_TRUE(std::is_move_assignable<v2::Result<uint32_t>>::value);
+ ASSERT_TRUE(std::is_copy_constructible<v2::Result<uint32_t>>::value);
+ ASSERT_TRUE(std::is_copy_assignable<v2::Result<uint32_t>>::value);
+}
+
+TEST(ResultTests, UnitTypeResult) {
+ v2::Result<v2::Unit> r(v2::Unit{});
+ ASSERT_TRUE(r);
+}
+
+struct RefCountData {
+ int ctor; // NOLINT(misc-non-private-member-variables-in-classes)
+ int copy_ctor; // NOLINT(misc-non-private-member-variables-in-classes)
+ int dtor; // NOLINT(misc-non-private-member-variables-in-classes)
+ int move; // NOLINT(misc-non-private-member-variables-in-classes)
+};
+
+class RefCountContainer {
+ public:
+ explicit RefCountContainer(RefCountData& data) : data_(data) {
+ ++data_.ctor;
+ }
+
+ RefCountContainer(RefCountContainer const&) = delete;
+
+ RefCountContainer(RefCountContainer&& rhs) noexcept : data_(rhs.data_) {
+ ++data_.copy_ctor;
+ }
+
+ RefCountContainer& operator=(RefCountContainer const&) = delete;
+
+ RefCountContainer& operator=(RefCountContainer&& rhs) noexcept {
+ data_ = rhs.data_;
+ ++data_.move;
+ return *this;
+ }
+
+ ~RefCountContainer() {
+ ++data_.dtor;
+ }
+
+ private:
+ RefCountData& data_;
+};
+
+TEST(ResultTests, ReferenceCount) {
+ ASSERT_TRUE(std::is_move_constructible<RefCountContainer>::value);
+ ASSERT_TRUE(std::is_move_assignable<RefCountContainer>::value);
+ ASSERT_FALSE(std::is_copy_constructible<RefCountContainer>::value);
+ ASSERT_FALSE(std::is_copy_assignable<RefCountContainer>::value);
+
+ RefCountData rc{0, 0, 0, 0};
+ { v2::Result<RefCountContainer> r(RefCountContainer{rc}); }
+ ASSERT_EQ(rc.ctor, 1);
+ ASSERT_EQ(rc.copy_ctor, 1);
+ ASSERT_EQ(rc.move, 0);
+ ASSERT_EQ(rc.dtor, 2);
+}
+
+v2::Result<Container> CreateContainer(bool succeed) {
+ if (!succeed) {
+ return v2::Error("foo");
+ }
+ return Container{42U};
+}
+
+TEST(ResultTests, FunctionReturn) {
+ auto r1 = CreateContainer(true);
+ ASSERT_TRUE(r1);
+ ASSERT_EQ(r1->value, 42U);
+
+ auto r2 = CreateContainer(false);
+ ASSERT_FALSE(r2);
+ ASSERT_EQ(r2.GetErrorMessage(), "foo");
+ ASSERT_EQ(r2.GetError().GetMessage(), "foo");
+}
+
+v2::Result<Container> FailToCreateContainer() {
+ auto container = CreateContainer(false);
+ if (!container) {
+ return v2::Error(container.GetError(), "bar");
+ }
+ return container;
+}
+
+TEST(ResultTests, CascadeError) {
+ auto container = FailToCreateContainer();
+ ASSERT_FALSE(container);
+ ASSERT_EQ(container.GetErrorMessage(), "foo -> bar");
+}
+
+struct NoCopyContainer {
+ uint32_t value; // NOLINT(misc-non-private-member-variables-in-classes)
+ DISALLOW_COPY_AND_ASSIGN(NoCopyContainer);
+};
+
+v2::Result<std::unique_ptr<NoCopyContainer>> CreateNoCopyContainer(bool succeed) {
+ if (!succeed) {
+ return v2::Error("foo");
+ }
+ std::unique_ptr<NoCopyContainer> p(new NoCopyContainer{0U});
+ p->value = 42U;
+ return std::move(p);
+}
+
+TEST(ResultTests, UniquePtr) {
+ auto r1 = CreateNoCopyContainer(true);
+ ASSERT_TRUE(r1);
+ ASSERT_EQ((*r1)->value, 42U);
+ (*r1)->value = 0U;
+ ASSERT_EQ((*r1)->value, 0U);
+
+ auto r2 = CreateNoCopyContainer(false);
+ ASSERT_FALSE(r2);
+ ASSERT_EQ(r2.GetErrorMessage(), "foo");
+}
+
+} // namespace android::idmap2
diff --git a/cmds/statsd/src/atom_field_options.proto b/cmds/statsd/src/atom_field_options.proto
index e33bd8c97a07..2a3eee2a7e18 100644
--- a/cmds/statsd/src/atom_field_options.proto
+++ b/cmds/statsd/src/atom_field_options.proto
@@ -82,4 +82,6 @@ extend google.protobuf.FieldOptions {
optional bool is_uid = 50001 [default = false];
optional LogMode log_mode = 50002 [default = MODE_AUTOMATIC];
+
+ optional bool allow_from_any_uid = 50003 [default = false];
} \ No newline at end of file
diff --git a/cmds/statsd/src/atoms.proto b/cmds/statsd/src/atoms.proto
index fc3aa91b9e0b..4f17d69f23f2 100644
--- a/cmds/statsd/src/atoms.proto
+++ b/cmds/statsd/src/atoms.proto
@@ -110,7 +110,7 @@ message Atom {
PacketWakeupOccurred packet_wakeup_occurred = 44;
WallClockTimeShifted wall_clock_time_shifted = 45;
AnomalyDetected anomaly_detected = 46;
- AppBreadcrumbReported app_breadcrumb_reported = 47;
+ AppBreadcrumbReported app_breadcrumb_reported = 47 [(allow_from_any_uid) = true];
AppStartOccurred app_start_occurred = 48;
AppStartCanceled app_start_canceled = 49;
AppStartFullyDrawn app_start_fully_drawn = 50;
@@ -121,7 +121,7 @@ message Atom {
AppStartMemoryStateCaptured app_start_memory_state_captured = 55;
ShutdownSequenceReported shutdown_sequence_reported = 56;
BootSequenceReported boot_sequence_reported = 57;
- DaveyOccurred davey_occurred = 58;
+ DaveyOccurred davey_occurred = 58 [(allow_from_any_uid) = true];
OverlayStateChanged overlay_state_changed = 59;
ForegroundServiceStateChanged foreground_service_state_changed = 60;
CallStateChanged call_state_changed = 61;
@@ -239,6 +239,7 @@ message Atom {
PermissionGrantRequestResultReported permission_grant_request_result_reported = 170;
BluetoothSocketConnectionStateChanged bluetooth_socket_connection_state_changed = 171;
DeviceIdentifierAccessDenied device_identifier_access_denied = 172;
+ BubbleDeveloperErrorReported bubble_developer_error_reported = 173;
}
// Pulled events will start at field 10000.
@@ -5344,6 +5345,27 @@ message BubbleUIChanged {
}
/**
+ * Logs System UI bubbles developer errors.
+ *
+ * Logged from:
+ * frameworks/base/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
+ */
+message BubbleDeveloperErrorReported {
+
+ // The app package that is posting the bubble.
+ optional string package_name = 1;
+
+ // Bubble developer error type enums.
+ enum Error {
+ UNKNOWN = 0;
+ ACTIVITY_INFO_MISSING = 1;
+ ACTIVITY_INFO_NOT_RESIZABLE = 2;
+ DOCUMENT_LAUNCH_NOT_ALWAYS = 3;
+ }
+ optional Error error = 2 [default = UNKNOWN];
+}
+
+/**
* Logs that a constraint for a scheduled job has changed.
*
* Logged from:
diff --git a/cmds/statsd/src/guardrail/StatsdStats.cpp b/cmds/statsd/src/guardrail/StatsdStats.cpp
index a5bd5c6b6364..37d5ba0e6801 100644
--- a/cmds/statsd/src/guardrail/StatsdStats.cpp
+++ b/cmds/statsd/src/guardrail/StatsdStats.cpp
@@ -443,6 +443,11 @@ void StatsdStats::noteBadValueType(int metricId) {
getAtomMetricStats(metricId).badValueType++;
}
+void StatsdStats::noteBucketDropped(int metricId) {
+ lock_guard<std::mutex> lock(mLock);
+ getAtomMetricStats(metricId).bucketDropped++;
+}
+
void StatsdStats::noteConditionChangeInNextBucket(int metricId) {
lock_guard<std::mutex> lock(mLock);
getAtomMetricStats(metricId).conditionChangeInNextBucket++;
diff --git a/cmds/statsd/src/guardrail/StatsdStats.h b/cmds/statsd/src/guardrail/StatsdStats.h
index cb17061c1ed1..20ea7e5df1fa 100644
--- a/cmds/statsd/src/guardrail/StatsdStats.h
+++ b/cmds/statsd/src/guardrail/StatsdStats.h
@@ -360,6 +360,11 @@ public:
void noteBadValueType(int atomId);
/**
+ * Buckets were dropped due to reclaim memory.
+ */
+ void noteBucketDropped(int metricId);
+
+ /**
* A condition change was too late, arrived in the wrong bucket and was skipped
*/
void noteConditionChangeInNextBucket(int atomId);
@@ -414,6 +419,7 @@ public:
long badValueType = 0;
long conditionChangeInNextBucket = 0;
long invalidatedBucket = 0;
+ long bucketDropped = 0;
} AtomMetricStats;
private:
diff --git a/cmds/statsd/src/metrics/CountMetricProducer.cpp b/cmds/statsd/src/metrics/CountMetricProducer.cpp
index 7cc57c12063c..350745b2c326 100644
--- a/cmds/statsd/src/metrics/CountMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/CountMetricProducer.cpp
@@ -243,6 +243,7 @@ void CountMetricProducer::onDumpReportLocked(const int64_t dumpTimeNs,
void CountMetricProducer::dropDataLocked(const int64_t dropTimeNs) {
flushIfNeededLocked(dropTimeNs);
+ StatsdStats::getInstance().noteBucketDropped(mMetricId);
mPastBuckets.clear();
}
diff --git a/cmds/statsd/src/metrics/DurationMetricProducer.cpp b/cmds/statsd/src/metrics/DurationMetricProducer.cpp
index 69bafc354643..6c1c47bbc093 100644
--- a/cmds/statsd/src/metrics/DurationMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/DurationMetricProducer.cpp
@@ -444,6 +444,7 @@ void DurationMetricProducer::onConditionChangedLocked(const bool conditionMet,
void DurationMetricProducer::dropDataLocked(const int64_t dropTimeNs) {
flushIfNeededLocked(dropTimeNs);
+ StatsdStats::getInstance().noteBucketDropped(mMetricId);
mPastBuckets.clear();
}
diff --git a/cmds/statsd/src/metrics/EventMetricProducer.cpp b/cmds/statsd/src/metrics/EventMetricProducer.cpp
index c53c4ce5e0d6..7e695a69988f 100644
--- a/cmds/statsd/src/metrics/EventMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/EventMetricProducer.cpp
@@ -77,6 +77,7 @@ EventMetricProducer::~EventMetricProducer() {
void EventMetricProducer::dropDataLocked(const int64_t dropTimeNs) {
mProto->clear();
+ StatsdStats::getInstance().noteBucketDropped(mMetricId);
}
void EventMetricProducer::onSlicedConditionMayChangeLocked(bool overallCondition,
diff --git a/cmds/statsd/src/metrics/GaugeMetricProducer.cpp b/cmds/statsd/src/metrics/GaugeMetricProducer.cpp
index c9b71659aa58..2609937924ac 100644
--- a/cmds/statsd/src/metrics/GaugeMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/GaugeMetricProducer.cpp
@@ -510,6 +510,7 @@ void GaugeMetricProducer::updateCurrentSlicedBucketForAnomaly() {
void GaugeMetricProducer::dropDataLocked(const int64_t dropTimeNs) {
flushIfNeededLocked(dropTimeNs);
+ StatsdStats::getInstance().noteBucketDropped(mMetricId);
mPastBuckets.clear();
}
diff --git a/cmds/statsd/src/metrics/MetricsManager.cpp b/cmds/statsd/src/metrics/MetricsManager.cpp
index ca681176c54a..6ed6ab500597 100644
--- a/cmds/statsd/src/metrics/MetricsManager.cpp
+++ b/cmds/statsd/src/metrics/MetricsManager.cpp
@@ -241,12 +241,22 @@ void MetricsManager::onDumpReport(const int64_t dumpTimeStampNs,
VLOG("=========================Metric Reports End==========================");
}
-// Consume the stats log if it's interesting to this metric.
-void MetricsManager::onLogEvent(const LogEvent& event) {
- if (!mConfigValid) {
- return;
+
+bool MetricsManager::checkLogCredentials(const LogEvent& event) {
+ if (android::util::AtomsInfo::kWhitelistedAtoms.find(event.GetTagId()) !=
+ android::util::AtomsInfo::kWhitelistedAtoms.end())
+ {
+ return true;
}
+ std::lock_guard<std::mutex> lock(mAllowedLogSourcesMutex);
+ if (mAllowedLogSources.find(event.GetUid()) == mAllowedLogSources.end()) {
+ VLOG("log source %d not on the whitelist", event.GetUid());
+ return false;
+ }
+ return true;
+}
+bool MetricsManager::eventSanityCheck(const LogEvent& event) {
if (event.GetTagId() == android::util::APP_BREADCRUMB_REPORTED) {
// Check that app breadcrumb reported fields are valid.
status_t err = NO_ERROR;
@@ -256,23 +266,23 @@ void MetricsManager::onLogEvent(const LogEvent& event) {
long appHookUid = event.GetLong(event.size()-2, &err);
if (err != NO_ERROR ) {
VLOG("APP_BREADCRUMB_REPORTED had error when parsing the uid");
- return;
+ return false;
}
int32_t loggerUid = event.GetUid();
if (loggerUid != appHookUid && loggerUid != AID_STATSD) {
VLOG("APP_BREADCRUMB_REPORTED has invalid uid: claimed %ld but caller is %d",
appHookUid, loggerUid);
- return;
+ return false;
}
// The state must be from 0,3. This part of code must be manually updated.
long appHookState = event.GetLong(event.size(), &err);
if (err != NO_ERROR ) {
VLOG("APP_BREADCRUMB_REPORTED had error when parsing the state field");
- return;
+ return false;
} else if (appHookState < 0 || appHookState > 3) {
VLOG("APP_BREADCRUMB_REPORTED does not have valid state %ld", appHookState);
- return;
+ return false;
}
} else if (event.GetTagId() == android::util::DAVEY_OCCURRED) {
// Daveys can be logged from any app since they are logged in libs/hwui/JankTracker.cpp.
@@ -283,31 +293,42 @@ void MetricsManager::onLogEvent(const LogEvent& event) {
long jankUid = event.GetLong(1, &err);
if (err != NO_ERROR ) {
VLOG("Davey occurred had error when parsing the uid");
- return;
+ return false;
}
int32_t loggerUid = event.GetUid();
if (loggerUid != jankUid && loggerUid != AID_STATSD) {
VLOG("DAVEY_OCCURRED has invalid uid: claimed %ld but caller is %d", jankUid,
loggerUid);
- return;
+ return false;
}
long duration = event.GetLong(event.size(), &err);
if (err != NO_ERROR ) {
VLOG("Davey occurred had error when parsing the duration");
- return;
+ return false;
} else if (duration > 100000) {
VLOG("Davey duration is unreasonably long: %ld", duration);
- return;
- }
- } else {
- std::lock_guard<std::mutex> lock(mAllowedLogSourcesMutex);
- if (mAllowedLogSources.find(event.GetUid()) == mAllowedLogSources.end()) {
- VLOG("log source %d not on the whitelist", event.GetUid());
- return;
+ return false;
}
}
+ return true;
+}
+
+// Consume the stats log if it's interesting to this metric.
+void MetricsManager::onLogEvent(const LogEvent& event) {
+ if (!mConfigValid) {
+ return;
+ }
+
+ if (!checkLogCredentials(event)) {
+ return;
+ }
+
+ if (!eventSanityCheck(event)) {
+ return;
+ }
+
int tagId = event.GetTagId();
int64_t eventTimeNs = event.GetElapsedTimestampNs();
diff --git a/cmds/statsd/src/metrics/MetricsManager.h b/cmds/statsd/src/metrics/MetricsManager.h
index 80982c37dc6a..fdc28ea7f219 100644
--- a/cmds/statsd/src/metrics/MetricsManager.h
+++ b/cmds/statsd/src/metrics/MetricsManager.h
@@ -49,6 +49,10 @@ public:
// Return whether the configuration is valid.
bool isConfigValid() const;
+ bool checkLogCredentials(const LogEvent& event);
+
+ bool eventSanityCheck(const LogEvent& event);
+
void onLogEvent(const LogEvent& event);
void onAnomalyAlarmFired(
diff --git a/cmds/statsd/src/metrics/ValueMetricProducer.cpp b/cmds/statsd/src/metrics/ValueMetricProducer.cpp
index 9fb78e780870..1bd3ef20a578 100644
--- a/cmds/statsd/src/metrics/ValueMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/ValueMetricProducer.cpp
@@ -175,6 +175,7 @@ void ValueMetricProducer::onSlicedConditionMayChangeLocked(bool overallCondition
void ValueMetricProducer::dropDataLocked(const int64_t dropTimeNs) {
flushIfNeededLocked(dropTimeNs);
+ StatsdStats::getInstance().noteBucketDropped(mMetricId);
mPastBuckets.clear();
}
@@ -434,6 +435,10 @@ void ValueMetricProducer::onDataPulled(const std::vector<std::shared_ptr<LogEven
}
}
mHasGlobalBase = true;
+
+ // We can probably flush the bucket. Since we used bucketEndTime when calling
+ // #onMatchedLogEventInternalLocked, the current bucket will not have been flushed.
+ flushIfNeededLocked(realEventTime);
} else {
VLOG("No need to commit data on condition false.");
}
diff --git a/cmds/statsd/src/metrics/ValueMetricProducer.h b/cmds/statsd/src/metrics/ValueMetricProducer.h
index d9bec5d588be..0cfefa9e3eb4 100644
--- a/cmds/statsd/src/metrics/ValueMetricProducer.h
+++ b/cmds/statsd/src/metrics/ValueMetricProducer.h
@@ -61,6 +61,7 @@ public:
if (!mSplitBucketForAppUpgrade) {
return;
}
+ flushIfNeededLocked(eventTimeNs - 1);
if (mIsPulled && mCondition) {
pullAndMatchEventsLocked(eventTimeNs - 1);
}
@@ -212,6 +213,7 @@ private:
FRIEND_TEST(ValueMetricProducerTest, TestEventsWithNonSlicedCondition);
FRIEND_TEST(ValueMetricProducerTest, TestPushedEventsWithUpgrade);
FRIEND_TEST(ValueMetricProducerTest, TestPulledValueWithUpgrade);
+ FRIEND_TEST(ValueMetricProducerTest, TestPartialBucketCreated);
FRIEND_TEST(ValueMetricProducerTest, TestPulledValueWithUpgradeWhileConditionFalse);
FRIEND_TEST(ValueMetricProducerTest, TestPulledWithAppUpgradeDisabled);
FRIEND_TEST(ValueMetricProducerTest, TestPushedEventsWithoutCondition);
@@ -238,6 +240,8 @@ private:
FRIEND_TEST(ValueMetricProducerTest, TestInvalidBucketWhenOneConditionFailed);
FRIEND_TEST(ValueMetricProducerTest, TestInvalidBucketWhenInitialPullFailed);
FRIEND_TEST(ValueMetricProducerTest, TestInvalidBucketWhenLastPullFailed);
+ FRIEND_TEST(ValueMetricProducerTest, TestResetBaseOnPullDelayExceeded);
+ FRIEND_TEST(ValueMetricProducerTest, TestBaseSetOnConditionChange);
};
} // namespace statsd
diff --git a/cmds/statsd/src/stats_log.proto b/cmds/statsd/src/stats_log.proto
index 5b9148283bdc..73aab4847e11 100644
--- a/cmds/statsd/src/stats_log.proto
+++ b/cmds/statsd/src/stats_log.proto
@@ -418,6 +418,7 @@ message StatsdStatsReport {
optional int64 bad_value_type = 5;
optional int64 condition_change_in_next_bucket = 6;
optional int64 invalidated_bucket = 7;
+ optional int64 bucket_dropped = 8;
}
repeated AtomMetricStats atom_metric_stats = 17;
diff --git a/cmds/statsd/src/stats_log_util.cpp b/cmds/statsd/src/stats_log_util.cpp
index 3cb7563b206b..f76a9ad78396 100644
--- a/cmds/statsd/src/stats_log_util.cpp
+++ b/cmds/statsd/src/stats_log_util.cpp
@@ -79,6 +79,7 @@ const int FIELD_ID_SKIPPED_FORWARD_BUCKETS = 4;
const int FIELD_ID_BAD_VALUE_TYPE = 5;
const int FIELD_ID_CONDITION_CHANGE_IN_NEXT_BUCKET = 6;
const int FIELD_ID_INVALIDATED_BUCKET = 7;
+const int FIELD_ID_BUCKET_DROPPED = 8;
namespace {
@@ -497,6 +498,8 @@ void writeAtomMetricStatsToStream(const std::pair<int, StatsdStats::AtomMetricSt
(long long)pair.second.conditionChangeInNextBucket);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_INVALIDATED_BUCKET,
(long long)pair.second.invalidatedBucket);
+ protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_BUCKET_DROPPED,
+ (long long)pair.second.bucketDropped);
protoOutput->end(token);
}
diff --git a/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp b/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp
index 64045520fb0b..91b98ecffa29 100644
--- a/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp
+++ b/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp
@@ -167,9 +167,10 @@ TEST(ValueMetricProducerTest, TestPulledEventsNoCondition) {
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(11, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(8, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
allData.clear();
event = make_shared<LogEvent>(tagId, bucket3StartTimeNs + 1);
@@ -184,11 +185,12 @@ TEST(ValueMetricProducerTest, TestPulledEventsNoCondition) {
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(23, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(12, curInterval.value.long_value);
EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
- EXPECT_EQ(1UL, valueProducer.mPastBuckets.begin()->second.size());
- EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second.back().values[0].long_value);
+ EXPECT_EQ(2UL, valueProducer.mPastBuckets.begin()->second.size());
+ EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
+ EXPECT_EQ(12, valueProducer.mPastBuckets.begin()->second.back().values[0].long_value);
allData.clear();
event = make_shared<LogEvent>(tagId, bucket4StartTimeNs + 1);
@@ -202,11 +204,80 @@ TEST(ValueMetricProducerTest, TestPulledEventsNoCondition) {
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(36, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(13, curInterval.value.long_value);
EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
- EXPECT_EQ(2UL, valueProducer.mPastBuckets.begin()->second.size());
- EXPECT_EQ(12, valueProducer.mPastBuckets.begin()->second.back().values[0].long_value);
+ EXPECT_EQ(3UL, valueProducer.mPastBuckets.begin()->second.size());
+ EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
+ EXPECT_EQ(12, valueProducer.mPastBuckets.begin()->second[1].values[0].long_value);
+ EXPECT_EQ(13, valueProducer.mPastBuckets.begin()->second[2].values[0].long_value);
+}
+
+TEST(ValueMetricProducerTest, TestPartialBucketCreated) {
+ ValueMetric metric;
+ metric.set_id(metricId);
+ metric.set_bucket(ONE_MINUTE);
+ metric.mutable_value_field()->set_field(tagId);
+ metric.mutable_value_field()->add_child()->set_field(2);
+ metric.set_max_pull_delay_sec(INT_MAX);
+
+ UidMap uidMap;
+ SimpleAtomMatcher atomMatcher;
+ atomMatcher.set_atom_id(tagId);
+ sp<EventMatcherWizard> eventMatcherWizard =
+ new EventMatcherWizard({new SimpleLogMatchingTracker(
+ atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
+ sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
+ sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
+ EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, _, _, _)).WillOnce(Return());
+ EXPECT_CALL(*pullerManager, UnRegisterReceiver(tagId, _)).WillRepeatedly(Return());
+ EXPECT_CALL(*pullerManager, Pull(tagId, _))
+ // Initialize bucket.
+ .WillOnce(Invoke([](int tagId, vector<std::shared_ptr<LogEvent>>* data) {
+ data->clear();
+ shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucketStartTimeNs + 1);
+ event->write(tagId);
+ event->write(1);
+ event->init();
+ data->push_back(event);
+ return true;
+ }))
+ // Partial bucket.
+ .WillOnce(Invoke([](int tagId, vector<std::shared_ptr<LogEvent>>* data) {
+ data->clear();
+ shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucket2StartTimeNs + 10);
+ event->write(tagId);
+ event->write(5);
+ event->init();
+ data->push_back(event);
+ return true;
+ }));
+
+ ValueMetricProducer valueProducer(kConfigKey, metric, -1 /*-1 meaning no condition*/, wizard,
+ logEventMatcherIndex, eventMatcherWizard, tagId,
+ bucketStartTimeNs, bucketStartTimeNs, pullerManager);
+
+ // First bucket ends.
+ vector<shared_ptr<LogEvent>> allData;
+ allData.clear();
+ shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucket2StartTimeNs + 10);
+ event->write(tagId);
+ event->write(2);
+ event->init();
+ allData.push_back(event);
+ valueProducer.onDataPulled(allData, /** success */ true);
+
+ // Partial buckets created in 2nd bucket.
+ valueProducer.notifyAppUpgrade(bucket2StartTimeNs + 2, "com.foo", 10000, 1);
+
+ // One full bucket and one partial bucket.
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ vector<ValueBucket> buckets = valueProducer.mPastBuckets.begin()->second;
+ EXPECT_EQ(2UL, buckets.size());
+ // Full bucket (2 - 1)
+ EXPECT_EQ(1, buckets[0].values[0].long_value);
+ // Full bucket (5 - 3)
+ EXPECT_EQ(3, buckets[1].values[0].long_value);
}
/*
@@ -264,9 +335,10 @@ TEST(ValueMetricProducerTest, TestPulledEventsWithFiltering) {
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(11, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(8, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
allData.clear();
event = make_shared<LogEvent>(tagId, bucket3StartTimeNs + 1);
@@ -275,16 +347,15 @@ TEST(ValueMetricProducerTest, TestPulledEventsWithFiltering) {
event->init();
allData.push_back(event);
valueProducer.onDataPulled(allData, /** succeed */ true);
- // has one slice
- EXPECT_EQ(1UL, valueProducer.mCurrentSlicedBucket.size());
- curInterval = valueProducer.mCurrentSlicedBucket.begin()->second[0];
+ // No new data seen, so data has been cleared.
+ EXPECT_EQ(0UL, valueProducer.mCurrentSlicedBucket.size());
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(11, curInterval.base.long_value);
- // no events caused flush of bucket
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(8, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
allData.clear();
event = make_shared<LogEvent>(tagId, bucket4StartTimeNs + 1);
@@ -363,9 +434,10 @@ TEST(ValueMetricProducerTest, TestPulledEventsTakeAbsoluteValueOnReset) {
curInterval = valueProducer.mCurrentSlicedBucket.begin()->second[0];
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(10, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(10, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(10, valueProducer.mPastBuckets.begin()->second.back().values[0].long_value);
allData.clear();
event = make_shared<LogEvent>(tagId, bucket4StartTimeNs + 1);
@@ -378,11 +450,12 @@ TEST(ValueMetricProducerTest, TestPulledEventsTakeAbsoluteValueOnReset) {
curInterval = valueProducer.mCurrentSlicedBucket.begin()->second[0];
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(36, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(26, curInterval.value.long_value);
EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
- EXPECT_EQ(1UL, valueProducer.mPastBuckets.begin()->second.size());
- EXPECT_EQ(10, valueProducer.mPastBuckets.begin()->second.back().values[0].long_value);
+ EXPECT_EQ(2UL, valueProducer.mPastBuckets.begin()->second.size());
+ EXPECT_EQ(10, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
+ EXPECT_EQ(26, valueProducer.mPastBuckets.begin()->second[1].values[0].long_value);
}
/*
@@ -456,9 +529,10 @@ TEST(ValueMetricProducerTest, TestPulledEventsTakeZeroOnReset) {
curInterval = valueProducer.mCurrentSlicedBucket.begin()->second[0];
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(36, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(26, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(26, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
}
/*
@@ -532,9 +606,10 @@ TEST(ValueMetricProducerTest, TestEventsWithNonSlicedCondition) {
curInterval = valueProducer.mCurrentSlicedBucket.begin()->second[0];
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(110, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
+ EXPECT_EQ(false, curInterval.hasValue);
EXPECT_EQ(10, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(10, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
valueProducer.onConditionChanged(false, bucket2StartTimeNs + 1);
@@ -651,8 +726,8 @@ TEST(ValueMetricProducerTest, TestPulledValueWithUpgrade) {
event->init();
allData.push_back(event);
valueProducer.onDataPulled(allData, /** succeed */ true);
- EXPECT_EQ(1UL, valueProducer.mPastBuckets[DEFAULT_METRIC_DIMENSION_KEY].size());
- EXPECT_EQ(bucket2StartTimeNs + 150, valueProducer.mCurrentBucketStartTimeNs);
+ EXPECT_EQ(2UL, valueProducer.mPastBuckets[DEFAULT_METRIC_DIMENSION_KEY].size());
+ EXPECT_EQ(bucket3StartTimeNs, valueProducer.mCurrentBucketStartTimeNs);
EXPECT_EQ(20L,
valueProducer.mPastBuckets[DEFAULT_METRIC_DIMENSION_KEY][0].values[0].long_value);
}
@@ -694,7 +769,7 @@ TEST(ValueMetricProducerTest, TestPulledWithAppUpgradeDisabled) {
valueProducer.notifyAppUpgrade(bucket2StartTimeNs + 150, "ANY.APP", 1, 1);
EXPECT_EQ(0UL, valueProducer.mPastBuckets[DEFAULT_METRIC_DIMENSION_KEY].size());
- EXPECT_EQ(bucketStartTimeNs, valueProducer.mCurrentBucketStartTimeNs);
+ EXPECT_EQ(bucket2StartTimeNs, valueProducer.mCurrentBucketStartTimeNs);
}
TEST(ValueMetricProducerTest, TestPulledValueWithUpgradeWhileConditionFalse) {
@@ -1018,9 +1093,9 @@ TEST(ValueMetricProducerTest, TestBucketBoundaryNoCondition) {
// tartUpdated:false sum:12
EXPECT_EQ(true, curInterval.hasBase);
EXPECT_EQ(23, curInterval.base.long_value);
- EXPECT_EQ(true, curInterval.hasValue);
- EXPECT_EQ(12, curInterval.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(false, curInterval.hasValue);
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(12, valueProducer.mPastBuckets.begin()->second.back().values[0].long_value);
// pull 3 come late.
// The previous bucket gets closed with error. (Has start value 23, no ending)
@@ -1681,7 +1756,7 @@ TEST(ValueMetricProducerTest, TestUseZeroDefaultBase) {
EXPECT_EQ(2UL, valueProducer.mCurrentSlicedBucket.size());
EXPECT_EQ(true, interval1.hasBase);
EXPECT_EQ(11, interval1.base.long_value);
- EXPECT_EQ(true, interval1.hasValue);
+ EXPECT_EQ(false, interval1.hasValue);
EXPECT_EQ(8, interval1.value.long_value);
auto it = valueProducer.mCurrentSlicedBucket.begin();
@@ -1695,9 +1770,14 @@ TEST(ValueMetricProducerTest, TestUseZeroDefaultBase) {
EXPECT_EQ(2, it->first.getDimensionKeyInWhat().getValues()[0].mValue.int_value);
EXPECT_EQ(true, interval2.hasBase);
EXPECT_EQ(4, interval2.base.long_value);
- EXPECT_EQ(true, interval2.hasValue);
+ EXPECT_EQ(false, interval2.hasValue);
EXPECT_EQ(4, interval2.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+
+ EXPECT_EQ(2UL, valueProducer.mPastBuckets.size());
+ auto iterator = valueProducer.mPastBuckets.begin();
+ EXPECT_EQ(8, iterator->second[0].values[0].long_value);
+ iterator++;
+ EXPECT_EQ(4, iterator->second[0].values[0].long_value);
}
/*
@@ -1766,7 +1846,7 @@ TEST(ValueMetricProducerTest, TestUseZeroDefaultBaseWithPullFailures) {
EXPECT_EQ(2UL, valueProducer.mCurrentSlicedBucket.size());
EXPECT_EQ(true, interval1.hasBase);
EXPECT_EQ(11, interval1.base.long_value);
- EXPECT_EQ(true, interval1.hasValue);
+ EXPECT_EQ(false, interval1.hasValue);
EXPECT_EQ(8, interval1.value.long_value);
auto it = valueProducer.mCurrentSlicedBucket.begin();
@@ -1780,9 +1860,9 @@ TEST(ValueMetricProducerTest, TestUseZeroDefaultBaseWithPullFailures) {
EXPECT_EQ(2, it->first.getDimensionKeyInWhat().getValues()[0].mValue.int_value);
EXPECT_EQ(true, interval2.hasBase);
EXPECT_EQ(4, interval2.base.long_value);
- EXPECT_EQ(true, interval2.hasValue);
+ EXPECT_EQ(false, interval2.hasValue);
EXPECT_EQ(4, interval2.value.long_value);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(2UL, valueProducer.mPastBuckets.size());
// next pull somehow did not happen, skip to end of bucket 3
allData.clear();
@@ -1793,11 +1873,11 @@ TEST(ValueMetricProducerTest, TestUseZeroDefaultBaseWithPullFailures) {
allData.push_back(event1);
valueProducer.onDataPulled(allData, /** succeed */ true);
- EXPECT_EQ(2UL, valueProducer.mCurrentSlicedBucket.size());
+ EXPECT_EQ(1UL, valueProducer.mCurrentSlicedBucket.size());
EXPECT_EQ(true, interval2.hasBase);
- EXPECT_EQ(5, interval2.base.long_value);
+ EXPECT_EQ(4, interval2.base.long_value);
EXPECT_EQ(false, interval2.hasValue);
- EXPECT_EQ(false, interval1.hasBase);
+ EXPECT_EQ(true, interval1.hasBase);
EXPECT_EQ(false, interval1.hasValue);
EXPECT_EQ(true, valueProducer.mHasGlobalBase);
EXPECT_EQ(2UL, valueProducer.mPastBuckets.size());
@@ -1817,13 +1897,13 @@ TEST(ValueMetricProducerTest, TestUseZeroDefaultBaseWithPullFailures) {
EXPECT_EQ(2UL, valueProducer.mCurrentSlicedBucket.size());
EXPECT_EQ(true, interval2.hasBase);
- EXPECT_EQ(13, interval2.base.long_value);
- EXPECT_EQ(true, interval2.hasValue);
- EXPECT_EQ(8, interval2.value.long_value);
+ EXPECT_EQ(5, interval2.base.long_value);
+ EXPECT_EQ(false, interval2.hasValue);
+ EXPECT_EQ(5, interval2.value.long_value);
EXPECT_EQ(true, interval1.hasBase);
- EXPECT_EQ(5, interval1.base.long_value);
- EXPECT_EQ(true, interval1.hasValue);
- EXPECT_EQ(5, interval1.value.long_value);
+ EXPECT_EQ(13, interval1.base.long_value);
+ EXPECT_EQ(false, interval1.hasValue);
+ EXPECT_EQ(8, interval1.value.long_value);
EXPECT_EQ(true, valueProducer.mHasGlobalBase);
EXPECT_EQ(2UL, valueProducer.mPastBuckets.size());
}
@@ -1892,9 +1972,11 @@ TEST(ValueMetricProducerTest, TestTrimUnusedDimensionKey) {
EXPECT_EQ(2UL, valueProducer.mCurrentSlicedBucket.size());
EXPECT_EQ(true, interval1.hasBase);
EXPECT_EQ(11, interval1.base.long_value);
- EXPECT_EQ(true, interval1.hasValue);
+ EXPECT_EQ(false, interval1.hasValue);
EXPECT_EQ(8, interval1.value.long_value);
- EXPECT_TRUE(interval1.seenNewData);
+ EXPECT_FALSE(interval1.seenNewData);
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(8, valueProducer.mPastBuckets.begin()->second[0].values[0].long_value);
auto it = valueProducer.mCurrentSlicedBucket.begin();
for (; it != valueProducer.mCurrentSlicedBucket.end(); it++) {
@@ -1908,8 +1990,8 @@ TEST(ValueMetricProducerTest, TestTrimUnusedDimensionKey) {
EXPECT_EQ(true, interval2.hasBase);
EXPECT_EQ(4, interval2.base.long_value);
EXPECT_EQ(false, interval2.hasValue);
- EXPECT_TRUE(interval2.seenNewData);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
+ EXPECT_FALSE(interval2.seenNewData);
+ EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
// next pull somehow did not happen, skip to end of bucket 3
allData.clear();
@@ -1920,35 +2002,34 @@ TEST(ValueMetricProducerTest, TestTrimUnusedDimensionKey) {
allData.push_back(event1);
valueProducer.onDataPulled(allData, /** succeed */ true);
- EXPECT_EQ(2UL, valueProducer.mCurrentSlicedBucket.size());
-
- EXPECT_EQ(false, interval1.hasBase);
- EXPECT_EQ(false, interval1.hasValue);
- EXPECT_EQ(8, interval1.value.long_value);
- // on probation now
- EXPECT_FALSE(interval1.seenNewData);
-
+ // Only one interval left. One was trimmed.
+ EXPECT_EQ(1UL, valueProducer.mCurrentSlicedBucket.size());
+ interval2 = valueProducer.mCurrentSlicedBucket.begin()->second[0];
+ EXPECT_EQ(2, it->first.getDimensionKeyInWhat().getValues()[0].mValue.int_value);
EXPECT_EQ(true, interval2.hasBase);
EXPECT_EQ(5, interval2.base.long_value);
EXPECT_EQ(false, interval2.hasValue);
- // back to good status
- EXPECT_TRUE(interval2.seenNewData);
+ EXPECT_FALSE(interval2.seenNewData);
EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
allData.clear();
event1 = make_shared<LogEvent>(tagId, bucket5StartTimeNs + 1);
event1->write(2);
- event1->write(13);
+ event1->write(14);
event1->init();
allData.push_back(event1);
valueProducer.onDataPulled(allData, /** succeed */ true);
- EXPECT_EQ(1UL, valueProducer.mCurrentSlicedBucket.size());
+ interval2 = valueProducer.mCurrentSlicedBucket.begin()->second[0];
EXPECT_EQ(true, interval2.hasBase);
- EXPECT_EQ(13, interval2.base.long_value);
- EXPECT_EQ(true, interval2.hasValue);
- EXPECT_EQ(8, interval2.value.long_value);
- EXPECT_EQ(1UL, valueProducer.mPastBuckets.size());
+ EXPECT_EQ(14, interval2.base.long_value);
+ EXPECT_EQ(false, interval2.hasValue);
+ EXPECT_FALSE(interval2.seenNewData);
+ EXPECT_EQ(2UL, valueProducer.mPastBuckets.size());
+ auto iterator = valueProducer.mPastBuckets.begin();
+ EXPECT_EQ(9, iterator->second[0].values[0].long_value);
+ iterator++;
+ EXPECT_EQ(8, iterator->second[0].values[0].long_value);
}
TEST(ValueMetricProducerTest, TestResetBaseOnPullFailAfterConditionChange_EndOfBucket) {
@@ -2110,7 +2191,7 @@ TEST(ValueMetricProducerTest, TestResetBaseOnPullFailBeforeConditionChange) {
EXPECT_EQ(false, valueProducer.mHasGlobalBase);
}
-TEST(ValueMetricProducerTest, TestResetBaseOnPullTooLate) {
+TEST(ValueMetricProducerTest, TestResetBaseOnPullDelayExceeded) {
ValueMetric metric;
metric.set_id(metricId);
metric.set_bucket(ONE_MINUTE);
@@ -2133,7 +2214,7 @@ TEST(ValueMetricProducerTest, TestResetBaseOnPullTooLate) {
EXPECT_CALL(*pullerManager, Pull(tagId, _))
.WillOnce(Invoke([](int tagId, vector<std::shared_ptr<LogEvent>>* data) {
data->clear();
- shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucket2StartTimeNs + 1);
+ shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucketStartTimeNs + 1);
event->write(tagId);
event->write(120);
event->init();
@@ -2145,35 +2226,91 @@ TEST(ValueMetricProducerTest, TestResetBaseOnPullTooLate) {
eventMatcherWizard, tagId, bucketStartTimeNs,
bucketStartTimeNs, pullerManager);
- valueProducer.mCondition = true;
- valueProducer.mHasGlobalBase = true;
+ valueProducer.mCondition = false;
- vector<shared_ptr<LogEvent>> allData;
- allData.clear();
- shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucket2StartTimeNs + 1);
- event->write(1);
- event->write(110);
- event->init();
- allData.push_back(event);
- valueProducer.onDataPulled(allData, /** succeed */ true);
+ // Max delay is set to 0 so pull will exceed max delay.
+ valueProducer.onConditionChanged(true, bucketStartTimeNs + 1);
+ EXPECT_EQ(0UL, valueProducer.mCurrentSlicedBucket.size());
+}
- // has one slice
+TEST(ValueMetricProducerTest, TestResetBaseOnPullTooLate) {
+ ValueMetric metric;
+ metric.set_id(metricId);
+ metric.set_bucket(ONE_MINUTE);
+ metric.mutable_value_field()->set_field(tagId);
+ metric.mutable_value_field()->add_child()->set_field(2);
+ metric.set_condition(StringToId("SCREEN_ON"));
+ metric.set_max_pull_delay_sec(INT_MAX);
+
+ UidMap uidMap;
+ SimpleAtomMatcher atomMatcher;
+ atomMatcher.set_atom_id(tagId);
+ sp<EventMatcherWizard> eventMatcherWizard =
+ new EventMatcherWizard({new SimpleLogMatchingTracker(
+ atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
+ sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
+ sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
+ EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, _, _, _)).WillOnce(Return());
+ EXPECT_CALL(*pullerManager, UnRegisterReceiver(tagId, _)).WillRepeatedly(Return());
+
+ ValueMetricProducer valueProducer(kConfigKey, metric, 1, wizard, logEventMatcherIndex,
+ eventMatcherWizard, tagId, bucket2StartTimeNs,
+ bucket2StartTimeNs, pullerManager);
+
+ valueProducer.mCondition = false;
+
+ // Event should be skipped since it is from previous bucket.
+ // Pull should not be called.
+ valueProducer.onConditionChanged(true, bucketStartTimeNs);
+ EXPECT_EQ(0UL, valueProducer.mCurrentSlicedBucket.size());
+}
+
+TEST(ValueMetricProducerTest, TestBaseSetOnConditionChange) {
+ ValueMetric metric;
+ metric.set_id(metricId);
+ metric.set_bucket(ONE_MINUTE);
+ metric.mutable_value_field()->set_field(tagId);
+ metric.mutable_value_field()->add_child()->set_field(2);
+ metric.set_condition(StringToId("SCREEN_ON"));
+ metric.set_max_pull_delay_sec(INT_MAX);
+
+ UidMap uidMap;
+ SimpleAtomMatcher atomMatcher;
+ atomMatcher.set_atom_id(tagId);
+ sp<EventMatcherWizard> eventMatcherWizard =
+ new EventMatcherWizard({new SimpleLogMatchingTracker(
+ atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
+ sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
+ sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
+ EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, _, _, _)).WillOnce(Return());
+ EXPECT_CALL(*pullerManager, UnRegisterReceiver(tagId, _)).WillRepeatedly(Return());
+ EXPECT_CALL(*pullerManager, Pull(tagId, _))
+ .WillOnce(Invoke([](int tagId, vector<std::shared_ptr<LogEvent>>* data) {
+ data->clear();
+ shared_ptr<LogEvent> event = make_shared<LogEvent>(tagId, bucketStartTimeNs + 1);
+ event->write(tagId);
+ event->write(100);
+ event->init();
+ data->push_back(event);
+ return true;
+ }));
+
+ ValueMetricProducer valueProducer(kConfigKey, metric, 1, wizard, logEventMatcherIndex,
+ eventMatcherWizard, tagId, bucketStartTimeNs,
+ bucketStartTimeNs, pullerManager);
+
+ valueProducer.mCondition = false;
+ valueProducer.mHasGlobalBase = false;
+
+ valueProducer.onConditionChanged(true, bucketStartTimeNs + 1);
+ valueProducer.mHasGlobalBase = true;
EXPECT_EQ(1UL, valueProducer.mCurrentSlicedBucket.size());
ValueMetricProducer::Interval& curInterval =
valueProducer.mCurrentSlicedBucket.begin()->second[0];
EXPECT_EQ(true, curInterval.hasBase);
- EXPECT_EQ(110, curInterval.base.long_value);
+ EXPECT_EQ(100, curInterval.base.long_value);
EXPECT_EQ(false, curInterval.hasValue);
- EXPECT_EQ(0UL, valueProducer.mPastBuckets.size());
EXPECT_EQ(true, valueProducer.mHasGlobalBase);
-
- valueProducer.onConditionChanged(false, bucket2StartTimeNs + 1);
-
- // has one slice
- EXPECT_EQ(1UL, valueProducer.mCurrentSlicedBucket.size());
- EXPECT_EQ(false, curInterval.hasValue);
- EXPECT_EQ(false, curInterval.hasBase);
- EXPECT_EQ(false, valueProducer.mHasGlobalBase);
}
TEST(ValueMetricProducerTest, TestInvalidBucketWhenOneConditionFailed) {
diff --git a/cmds/svc/src/com/android/commands/svc/PowerCommand.java b/cmds/svc/src/com/android/commands/svc/PowerCommand.java
index 920a52dad641..d29e68e5a187 100644
--- a/cmds/svc/src/com/android/commands/svc/PowerCommand.java
+++ b/cmds/svc/src/com/android/commands/svc/PowerCommand.java
@@ -19,6 +19,7 @@ package com.android.commands.svc;
import android.content.Context;
import android.os.BatteryManager;
import android.os.IPowerManager;
+import android.os.PowerManager;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.os.SystemClock;
@@ -71,7 +72,8 @@ public class PowerCommand extends Svc.Command {
if (val != 0) {
// if the request is not to set it to false, wake up the screen so that
// it can stay on as requested
- pm.wakeUp(SystemClock.uptimeMillis(), "PowerCommand", null);
+ pm.wakeUp(SystemClock.uptimeMillis(),
+ PowerManager.WAKE_REASON_UNKNOWN, "PowerCommand", null);
}
pm.setStayOnSetting(val);
}
diff --git a/config/hiddenapi-greylist.txt b/config/hiddenapi-greylist.txt
index aad412f15fe2..a0d8a1232257 100644
--- a/config/hiddenapi-greylist.txt
+++ b/config/hiddenapi-greylist.txt
@@ -828,7 +828,6 @@ Landroid/os/IPowerManager;->isInteractive()Z
Landroid/os/IPowerManager;->reboot(ZLjava/lang/String;Z)V
Landroid/os/IPowerManager;->releaseWakeLock(Landroid/os/IBinder;I)V
Landroid/os/IPowerManager;->userActivity(JII)V
-Landroid/os/IPowerManager;->wakeUp(JLjava/lang/String;Ljava/lang/String;)V
Landroid/os/IRecoverySystem$Stub;->asInterface(Landroid/os/IBinder;)Landroid/os/IRecoverySystem;
Landroid/os/IRemoteCallback$Stub;-><init>()V
Landroid/os/IRemoteCallback;->sendResult(Landroid/os/Bundle;)V
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index 21d66e567a81..cc419b8d837a 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -4565,16 +4565,25 @@ public final class ActivityThread extends ClientTransactionHandler {
}
private void onCoreSettingsChange() {
- boolean debugViewAttributes =
- mCoreSettings.getInt(Settings.Global.DEBUG_VIEW_ATTRIBUTES, 0) != 0;
- if (debugViewAttributes != View.mDebugViewAttributes) {
- View.mDebugViewAttributes = debugViewAttributes;
-
+ if (updateDebugViewAttributeState()) {
// request all activities to relaunch for the changes to take place
relaunchAllActivities();
}
}
+ private boolean updateDebugViewAttributeState() {
+ boolean previousState = View.sDebugViewAttributes;
+
+ View.sDebugViewAttributesApplicationPackage = mCoreSettings.getString(
+ Settings.Global.DEBUG_VIEW_ATTRIBUTES_APPLICATION_PACKAGE, "");
+ String currentPackage = (mBoundApplication != null && mBoundApplication.appInfo != null)
+ ? mBoundApplication.appInfo.packageName : "";
+ View.sDebugViewAttributes =
+ mCoreSettings.getInt(Settings.Global.DEBUG_VIEW_ATTRIBUTES, 0) != 0
+ || View.sDebugViewAttributesApplicationPackage.equals(currentPackage);
+ return previousState != View.sDebugViewAttributes;
+ }
+
private void relaunchAllActivities() {
for (Map.Entry<IBinder, ActivityClientRecord> entry : mActivities.entrySet()) {
final Activity activity = entry.getValue().activity;
@@ -5950,8 +5959,7 @@ public final class ActivityThread extends ClientTransactionHandler {
// true : use 24 hour format.
DateFormat.set24HourTimePref(is24Hr);
- View.mDebugViewAttributes =
- mCoreSettings.getInt(Settings.Global.DEBUG_VIEW_ATTRIBUTES, 0) != 0;
+ updateDebugViewAttributeState();
StrictMode.initThreadDefaults(data.appInfo);
StrictMode.initVmDefaults(data.appInfo);
diff --git a/core/java/android/content/Intent.java b/core/java/android/content/Intent.java
index a3021f371e19..d781a96420c7 100644
--- a/core/java/android/content/Intent.java
+++ b/core/java/android/content/Intent.java
@@ -817,28 +817,6 @@ public class Intent implements Parcelable, Cloneable {
= "android.intent.action.SHOW_APP_INFO";
/**
- * Activity Action: Start an activity to show the app's detailed usage information for
- * permission protected data.
- *
- * The Intent contains an extra {@link #EXTRA_PERMISSION_USAGE_PERMISSIONS} that is of
- * type {@code String[]} and contains the specific permissions to show information for.
- *
- * Apps should handle this intent if they want to provide more information about permission
- * usage to users beyond the information provided in the manifest.
- */
- @SdkConstant(SdkConstantType.ACTIVITY_INTENT_ACTION)
- public static final String ACTION_PERMISSION_USAGE_DETAILS =
- "android.intent.action.PERMISSION_USAGE_DETAILS";
-
- /**
- * The name of the extra used to contain the permissions in
- * {@link #ACTION_PERMISSION_USAGE_DETAILS}.
- * @see #ACTION_PERMISSION_USAGE_DETAILS
- */
- public static final String EXTRA_PERMISSION_USAGE_PERMISSIONS =
- "android.intent.extra.PERMISSION_USAGE_PERMISSIONS";
-
- /**
* Represents a shortcut/live folder icon resource.
*
* @see Intent#ACTION_CREATE_SHORTCUT
diff --git a/core/java/android/content/pm/PackageInfo.java b/core/java/android/content/pm/PackageInfo.java
index 6d22277a5384..27a5b392855e 100644
--- a/core/java/android/content/pm/PackageInfo.java
+++ b/core/java/android/content/pm/PackageInfo.java
@@ -204,10 +204,7 @@ public class PackageInfo implements Parcelable {
* {@link PackageManager#GET_PERMISSIONS} was set. This list includes
* all permissions requested, even those that were not granted or known
* by the system at install time.
- *
- * @deprecated Use {@link #usesPermissions}
*/
- @Deprecated
public String[] requestedPermissions;
/**
@@ -217,23 +214,10 @@ public class PackageInfo implements Parcelable {
* {@link PackageManager#GET_PERMISSIONS} was set. Each value matches
* the corresponding entry in {@link #requestedPermissions}, and will have
* the flag {@link #REQUESTED_PERMISSION_GRANTED} set as appropriate.
- *
- * @deprecated Use {@link #usesPermissions}
*/
- @Deprecated
public int[] requestedPermissionsFlags;
/**
- * Array of all {@link android.R.styleable#AndroidManifestUsesPermission
- * &lt;uses-permission&gt;} tags included under &lt;manifest&gt;,
- * or null if there were none. This is only filled in if the flag
- * {@link PackageManager#GET_PERMISSIONS} was set. This list includes
- * all permissions requested, even those that were not granted or known
- * by the system at install time.
- */
- public UsesPermissionInfo[] usesPermissions;
-
- /**
* Flag for {@link #requestedPermissionsFlags}: the requested permission
* is required for the application to run; the user can not optionally
* disable it. Currently all permissions are required.
@@ -480,7 +464,6 @@ public class PackageInfo implements Parcelable {
dest.writeTypedArray(permissions, parcelableFlags);
dest.writeStringArray(requestedPermissions);
dest.writeIntArray(requestedPermissionsFlags);
- dest.writeTypedArray(usesPermissions, parcelableFlags);
dest.writeTypedArray(signatures, parcelableFlags);
dest.writeTypedArray(configPreferences, parcelableFlags);
dest.writeTypedArray(reqFeatures, parcelableFlags);
@@ -545,7 +528,6 @@ public class PackageInfo implements Parcelable {
permissions = source.createTypedArray(PermissionInfo.CREATOR);
requestedPermissions = source.createStringArray();
requestedPermissionsFlags = source.createIntArray();
- usesPermissions = source.createTypedArray(UsesPermissionInfo.CREATOR);
signatures = source.createTypedArray(Signature.CREATOR);
configPreferences = source.createTypedArray(ConfigurationInfo.CREATOR);
reqFeatures = source.createTypedArray(FeatureInfo.CREATOR);
diff --git a/core/java/android/content/pm/PackageParser.java b/core/java/android/content/pm/PackageParser.java
index 81ed110d15ec..5020a94c3469 100644
--- a/core/java/android/content/pm/PackageParser.java
+++ b/core/java/android/content/pm/PackageParser.java
@@ -791,23 +791,18 @@ public class PackageParser {
pi.permissions[i] = generatePermissionInfo(p.permissions.get(i), flags);
}
}
- N = p.usesPermissionInfos.size();
+ N = p.requestedPermissions.size();
if (N > 0) {
pi.requestedPermissions = new String[N];
pi.requestedPermissionsFlags = new int[N];
- pi.usesPermissions = new UsesPermissionInfo[N];
for (int i=0; i<N; i++) {
- UsesPermissionInfo info = p.usesPermissionInfos.get(i);
- final String perm = info.getPermission();
+ final String perm = p.requestedPermissions.get(i);
pi.requestedPermissions[i] = perm;
- int permissionFlags = 0;
// The notion of required permissions is deprecated but for compatibility.
- permissionFlags |= PackageInfo.REQUESTED_PERMISSION_REQUIRED;
+ pi.requestedPermissionsFlags[i] |= PackageInfo.REQUESTED_PERMISSION_REQUIRED;
if (grantedPermissions != null && grantedPermissions.contains(perm)) {
- permissionFlags |= PackageInfo.REQUESTED_PERMISSION_GRANTED;
+ pi.requestedPermissionsFlags[i] |= PackageInfo.REQUESTED_PERMISSION_GRANTED;
}
- pi.requestedPermissionsFlags[i] = permissionFlags;
- pi.usesPermissions[i] = new UsesPermissionInfo(info, permissionFlags);
}
}
}
@@ -2175,12 +2170,12 @@ public class PackageParser {
return null;
}
} else if (tagName.equals(TAG_USES_PERMISSION)) {
- if (!parseUsesPermission(pkg, res, parser, outError)) {
+ if (!parseUsesPermission(pkg, res, parser)) {
return null;
}
} else if (tagName.equals(TAG_USES_PERMISSION_SDK_M)
|| tagName.equals(TAG_USES_PERMISSION_SDK_23)) {
- if (!parseUsesPermission(pkg, res, parser, outError)) {
+ if (!parseUsesPermission(pkg, res, parser)) {
return null;
}
} else if (tagName.equals(TAG_USES_CONFIGURATION)) {
@@ -2498,7 +2493,7 @@ public class PackageParser {
newPermsMsg.append(' ');
}
newPermsMsg.append(npi.name);
- addRequestedPermission(pkg, npi.name);
+ pkg.requestedPermissions.add(npi.name);
pkg.implicitPermissions.add(npi.name);
}
}
@@ -2519,7 +2514,7 @@ public class PackageParser {
for (int in = 0; in < newPerms.size(); in++) {
final String perm = newPerms.get(in);
if (!pkg.requestedPermissions.contains(perm)) {
- addRequestedPermission(pkg, perm);
+ pkg.requestedPermissions.add(perm);
pkg.implicitPermissions.add(perm);
}
}
@@ -2599,13 +2594,13 @@ public class PackageParser {
}
} else {
if (FORCE_AUDIO_PACKAGES.contains(pkg.packageName)) {
- addRequestedPermission(pkg, android.Manifest.permission.READ_MEDIA_AUDIO);
+ pkg.requestedPermissions.add(android.Manifest.permission.READ_MEDIA_AUDIO);
}
if (FORCE_VIDEO_PACKAGES.contains(pkg.packageName)) {
- addRequestedPermission(pkg, android.Manifest.permission.READ_MEDIA_VIDEO);
+ pkg.requestedPermissions.add(android.Manifest.permission.READ_MEDIA_VIDEO);
}
if (FORCE_IMAGES_PACKAGES.contains(pkg.packageName)) {
- addRequestedPermission(pkg, android.Manifest.permission.READ_MEDIA_IMAGES);
+ pkg.requestedPermissions.add(android.Manifest.permission.READ_MEDIA_IMAGES);
}
}
@@ -2645,12 +2640,6 @@ public class PackageParser {
}
/**
- * Helper method for adding a requested permission to a package outside of a uses-permission.
- */
- private void addRequestedPermission(Package pkg, String permission) {
- pkg.requestedPermissions.add(permission);
- pkg.usesPermissionInfos.add(new UsesPermissionInfo(permission));
- }
/**
* Matches a given {@code targetCode} against a set of release codeNames. Target codes can
@@ -2987,8 +2976,8 @@ public class PackageParser {
return certSha256Digests;
}
- private boolean parseUsesPermission(Package pkg, Resources res, XmlResourceParser parser,
- String[] outError) throws XmlPullParserException, IOException {
+ private boolean parseUsesPermission(Package pkg, Resources res, XmlResourceParser parser)
+ throws XmlPullParserException, IOException {
TypedArray sa = res.obtainAttributes(parser,
com.android.internal.R.styleable.AndroidManifestUsesPermission);
@@ -3012,44 +3001,6 @@ public class PackageParser {
final String requiredNotfeature = sa.getNonConfigurationString(
com.android.internal.R.styleable.AndroidManifestUsesPermission_requiredNotFeature, 0);
- int dataSentOffDevice = sa.getInt(
- com.android.internal.R.styleable.AndroidManifestUsesPermission_dataSentOffDevice, 0);
-
- int dataSharedWithThirdParty = sa.getInt(
- com.android.internal.R.styleable.AndroidManifestUsesPermission_dataSharedWithThirdParty, 0);
-
- int dataUsedForMonetization = sa.getInt(
- com.android.internal.R.styleable.AndroidManifestUsesPermission_dataUsedForMonetization, 0);
-
- int retentionWeeks = -1;
- int retention;
-
- String rawRetention = sa.getString(
- com.android.internal.R.styleable.AndroidManifestUsesPermission_dataRetentionTime);
-
- if (rawRetention == null) {
- retention = UsesPermissionInfo.RETENTION_UNDEFINED;
- } else if ("notRetained".equals(rawRetention)) {
- retention = UsesPermissionInfo.RETENTION_NOT_RETAINED;
- } else if ("userSelected".equals(rawRetention)) {
- retention = UsesPermissionInfo.RETENTION_USER_SELECTED;
- } else if ("unlimited".equals(rawRetention)) {
- retention = UsesPermissionInfo.RETENTION_UNLIMITED;
- } else {
- // A number of weeks was specified
- retention = UsesPermissionInfo.RETENTION_SPECIFIED;
- retentionWeeks = sa.getInt(
- com.android.internal.R.styleable.AndroidManifestUsesPermission_dataRetentionTime,
- -1);
-
- if (retentionWeeks < 0) {
- outError[0] = "Bad value provided for dataRetentionTime.";
- mParseError = PackageManager.INSTALL_PARSE_FAILED_MANIFEST_MALFORMED;
- XmlUtils.skipCurrentTag(parser);
- sa.recycle();
- return false;
- }
- }
sa.recycle();
XmlUtils.skipCurrentTag(parser);
@@ -3082,10 +3033,6 @@ public class PackageParser {
+ parser.getPositionDescription());
}
- UsesPermissionInfo info = new UsesPermissionInfo(name, dataSentOffDevice,
- dataSharedWithThirdParty, dataUsedForMonetization, retention, retentionWeeks);
- pkg.usesPermissionInfos.add(info);
-
return true;
}
@@ -3420,10 +3367,6 @@ public class PackageParser {
perm.info.flags = sa.getInt(
com.android.internal.R.styleable.AndroidManifestPermission_permissionFlags, 0);
- perm.info.usageInfoRequired = sa.getInt(
- com.android.internal.R.styleable.AndroidManifestPermission_usageInfoRequired, 0)
- != 0;
-
sa.recycle();
if (perm.info.protectionLevel == -1) {
@@ -6625,9 +6568,6 @@ public class PackageParser {
@UnsupportedAppUsage
public final ArrayList<String> requestedPermissions = new ArrayList<String>();
- public final ArrayList<UsesPermissionInfo> usesPermissionInfos =
- new ArrayList<>();
-
/** Permissions requested but not in the manifest. */
public final ArrayList<String> implicitPermissions = new ArrayList<>();
@@ -7159,7 +7099,6 @@ public class PackageParser {
dest.readStringList(requestedPermissions);
internStringArrayList(requestedPermissions);
- dest.readParcelableList(usesPermissionInfos, boot);
dest.readStringList(implicitPermissions);
internStringArrayList(implicitPermissions);
protectedBroadcasts = dest.createStringArrayList();
@@ -7327,7 +7266,6 @@ public class PackageParser {
dest.writeParcelableList(instrumentation, flags);
dest.writeStringList(requestedPermissions);
- dest.writeParcelableList(usesPermissionInfos, flags);
dest.writeStringList(implicitPermissions);
dest.writeStringList(protectedBroadcasts);
diff --git a/core/java/android/content/pm/PermissionInfo.java b/core/java/android/content/pm/PermissionInfo.java
index fb63e0dad9b6..e24523406ab8 100644
--- a/core/java/android/content/pm/PermissionInfo.java
+++ b/core/java/android/content/pm/PermissionInfo.java
@@ -20,7 +20,6 @@ import android.annotation.IntDef;
import android.annotation.SystemApi;
import android.annotation.TestApi;
import android.annotation.UnsupportedAppUsage;
-import android.os.Build;
import android.os.Parcel;
import android.os.Parcelable;
import android.text.TextUtils;
@@ -368,12 +367,6 @@ public class PermissionInfo extends PackageItemInfo implements Parcelable {
*/
public CharSequence nonLocalizedDescription;
- /**
- * If {@code true} an application targeting {@link Build.VERSION_CODES#Q} <em>must</em>
- * include permission data usage information in order to be able to be granted this permission.
- */
- public boolean usageInfoRequired;
-
/** @hide */
public static int fixProtectionLevel(int level) {
if (level == PROTECTION_SIGNATURE_OR_SYSTEM) {
@@ -475,7 +468,6 @@ public class PermissionInfo extends PackageItemInfo implements Parcelable {
descriptionRes = orig.descriptionRes;
requestRes = orig.requestRes;
nonLocalizedDescription = orig.nonLocalizedDescription;
- usageInfoRequired = orig.usageInfoRequired;
}
/**
@@ -540,7 +532,6 @@ public class PermissionInfo extends PackageItemInfo implements Parcelable {
dest.writeInt(descriptionRes);
dest.writeInt(requestRes);
TextUtils.writeToParcel(nonLocalizedDescription, dest, parcelableFlags);
- dest.writeInt(usageInfoRequired ? 1 : 0);
}
/** @hide */
@@ -581,6 +572,5 @@ public class PermissionInfo extends PackageItemInfo implements Parcelable {
descriptionRes = source.readInt();
requestRes = source.readInt();
nonLocalizedDescription = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(source);
- usageInfoRequired = source.readInt() != 0;
}
}
diff --git a/core/java/android/content/pm/UsesPermissionInfo.java b/core/java/android/content/pm/UsesPermissionInfo.java
deleted file mode 100644
index d08548fa31a5..000000000000
--- a/core/java/android/content/pm/UsesPermissionInfo.java
+++ /dev/null
@@ -1,275 +0,0 @@
-/*
- * Copyright (C) 2018 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.content.pm;
-
-import android.annotation.IntDef;
-import android.os.Parcel;
-import android.os.Parcelable;
-
-import java.lang.annotation.RetentionPolicy;
-/**
- * Information you can retrive about a particular application requested permission. This
- * corresponds to information collected from the AndroidManifest.xml's &lt;uses-permission&gt;
- * tags.
- */
-public final class UsesPermissionInfo extends PackageItemInfo implements Parcelable {
-
- /**
- * Flag for {@link #getFlags()}: the requested permission is currently granted to the
- * application.
- */
- public static final int FLAG_REQUESTED_PERMISSION_GRANTED = 1 << 1;
-
- /** @hide */
- @IntDef(flag = true, prefix = {"FLAG_"}, value = {FLAG_REQUESTED_PERMISSION_GRANTED})
- @java.lang.annotation.Retention(RetentionPolicy.SOURCE)
- public @interface Flags {}
-
- /** An unset value for {@link #getDataSentOffDevice()},
- * {@link #getDataSharedWithThirdParty()}, and {@link #getDataUsedForMonetization()}
- */
- public static final int USAGE_UNDEFINED = 0;
-
- /**
- * A yes value for {@link #getDataSentOffDevice()}, {@link #getDataSharedWithThirdParty()},
- * and {@link #getDataUsedForMonetization()} corresponding to the <code>yes</code> value of
- * {@link android.R.attr#dataSentOffDevice}, {@link android.R.attr#dataSharedWithThirdParty},
- * and {@link android.R.attr#dataUsedForMonetization} attributes.
- */
- public static final int USAGE_YES = 1;
-
- /**
- * A user triggered only value for {@link #getDataSentOffDevice()},
- * {@link #getDataSharedWithThirdParty()}, and {@link #getDataUsedForMonetization()}
- * corresponding to the <code>userTriggered</code> value of
- * {@link android.R.attr#dataSentOffDevice}, {@link android.R.attr#dataSharedWithThirdParty},
- * and {@link android.R.attr#dataUsedForMonetization} attributes.
- */
- public static final int USAGE_USER_TRIGGERED = 2;
-
- /**
- * A no value for {@link #getDataSentOffDevice()}, {@link #getDataSharedWithThirdParty()},
- * and {@link #getDataUsedForMonetization()} corresponding to the <code>no</code> value of
- * {@link android.R.attr#dataSentOffDevice}, {@link android.R.attr#dataSharedWithThirdParty},
- * and {@link android.R.attr#dataUsedForMonetization} attributes.
- */
- public static final int USAGE_NO = 3;
-
- /** @hide */
- @IntDef(prefix = {"USAGE_"}, value = {
- USAGE_UNDEFINED,
- USAGE_YES,
- USAGE_USER_TRIGGERED,
- USAGE_NO})
- @java.lang.annotation.Retention(RetentionPolicy.SOURCE)
- public @interface Usage {}
-
- /**
- * An unset value for {@link #getDataRetention}.
- */
- public static final int RETENTION_UNDEFINED = 0;
-
- /**
- * A data not retained value for {@link #getDataRetention()} corresponding to the
- * <code>notRetained</code> value of {@link android.R.attr#dataRetentionTime}.
- */
- public static final int RETENTION_NOT_RETAINED = 1;
-
- /**
- * A user selected value for {@link #getDataRetention()} corresponding to the
- * <code>userSelected</code> value of {@link android.R.attr#dataRetentionTime}.
- */
- public static final int RETENTION_USER_SELECTED = 2;
-
- /**
- * An unlimited value for {@link #getDataRetention()} corresponding to the
- * <code>unlimited</code> value of {@link android.R.attr#dataRetentionTime}.
- */
- public static final int RETENTION_UNLIMITED = 3;
-
- /**
- * A specified value for {@link #getDataRetention()} corresponding to providing the number of
- * weeks data is retained in {@link android.R.attr#dataRetentionTime}. The number of weeks
- * is available in {@link #getDataRetentionWeeks()}.
- */
- public static final int RETENTION_SPECIFIED = 4;
-
- /** @hide */
- @IntDef(prefix = {"RETENTION_"}, value = {
- RETENTION_UNDEFINED,
- RETENTION_NOT_RETAINED,
- RETENTION_USER_SELECTED,
- RETENTION_UNLIMITED,
- RETENTION_SPECIFIED})
- @java.lang.annotation.Retention(RetentionPolicy.SOURCE)
- public @interface Retention {}
-
- private final String mPermission;
- private final @Flags int mFlags;
- private final @Usage int mDataSentOffDevice;
- private final @Usage int mDataSharedWithThirdParty;
- private final @Usage int mDataUsedForMonetization;
- private final @Retention int mDataRetention;
- private final int mDataRetentionWeeks;
-
- /** @hide */
- public UsesPermissionInfo(String permission) {
- mPermission = permission;
- mDataSentOffDevice = USAGE_UNDEFINED;
- mDataSharedWithThirdParty = USAGE_UNDEFINED;
- mDataUsedForMonetization = USAGE_UNDEFINED;
- mDataRetention = RETENTION_UNDEFINED;
- mDataRetentionWeeks = -1;
- mFlags = 0;
- }
-
- /** @hide */
- public UsesPermissionInfo(String permission,
- @Usage int dataSentOffDevice, @Usage int dataSharedWithThirdParty,
- @Usage int dataUsedForMonetization, @Retention int dataRetention,
- int dataRetentionWeeks) {
- mPermission = permission;
- mDataSentOffDevice = dataSentOffDevice;
- mDataSharedWithThirdParty = dataSharedWithThirdParty;
- mDataUsedForMonetization = dataUsedForMonetization;
- mDataRetention = dataRetention;
- mDataRetentionWeeks = dataRetentionWeeks;
- mFlags = 0;
- }
-
- /** @hide */
- public UsesPermissionInfo(UsesPermissionInfo orig) {
- this(orig, orig.mFlags);
- }
-
- /** @hide */
- public UsesPermissionInfo(UsesPermissionInfo orig, int flags) {
- super(orig);
- mPermission = orig.mPermission;
- mFlags = flags;
- mDataSentOffDevice = orig.mDataSentOffDevice;
- mDataSharedWithThirdParty = orig.mDataSharedWithThirdParty;
- mDataUsedForMonetization = orig.mDataUsedForMonetization;
- mDataRetention = orig.mDataRetention;
- mDataRetentionWeeks = orig.mDataRetentionWeeks;
- }
-
- /**
- * The name of the requested permission.
- */
- public String getPermission() {
- return mPermission;
- }
-
- public @Flags int getFlags() {
- return mFlags;
- }
-
- /**
- * If the application sends the data guarded by this permission off the device.
- *
- * See {@link android.R.attr#dataSentOffDevice}
- */
- public @Usage int getDataSentOffDevice() {
- return mDataSentOffDevice;
- }
-
- /**
- * If the application or its services shares the data guarded by this permission with third
- * parties.
- *
- * See {@link android.R.attr#dataSharedWithThirdParty}
- */
- public @Usage int getDataSharedWithThirdParty() {
- return mDataSharedWithThirdParty;
- }
-
- /**
- * If the application or its services use the data guarded by this permission for monetization
- * purposes.
- *
- * See {@link android.R.attr#dataUsedForMonetization}
- */
- public @Usage int getDataUsedForMonetization() {
- return mDataUsedForMonetization;
- }
-
- /**
- * How long the application or its services store the data guarded by this permission.
- * If set to {@link #RETENTION_SPECIFIED} {@link #getDataRetentionWeeks()} will contain the
- * number of weeks the data is stored.
- *
- * See {@link android.R.attr#dataRetentionTime}
- */
- public @Retention int getDataRetention() {
- return mDataRetention;
- }
-
- /**
- * If {@link #getDataRetention()} is {@link #RETENTION_SPECIFIED} the number of weeks the
- * application or its services store data guarded by this permission.
- *
- * @throws IllegalStateException if {@link #getDataRetention} is not
- * {@link #RETENTION_SPECIFIED}.
- */
- public int getDataRetentionWeeks() {
- if (mDataRetention != RETENTION_SPECIFIED) {
- throw new IllegalStateException("Data retention weeks not specified");
- }
- return mDataRetentionWeeks;
- }
-
- @Override
- public int describeContents() {
- return 0;
- }
-
- @Override
- public void writeToParcel(Parcel dest, int flags) {
- super.writeToParcel(dest, flags);
- dest.writeString(mPermission);
- dest.writeInt(mFlags);
- dest.writeInt(mDataSentOffDevice);
- dest.writeInt(mDataSharedWithThirdParty);
- dest.writeInt(mDataUsedForMonetization);
- dest.writeInt(mDataRetention);
- dest.writeInt(mDataRetentionWeeks);
- }
-
- private UsesPermissionInfo(Parcel source) {
- super(source);
- mPermission = source.readString();
- mFlags = source.readInt();
- mDataSentOffDevice = source.readInt();
- mDataSharedWithThirdParty = source.readInt();
- mDataUsedForMonetization = source.readInt();
- mDataRetention = source.readInt();
- mDataRetentionWeeks = source.readInt();
- }
-
- public static final Creator<UsesPermissionInfo> CREATOR =
- new Creator<UsesPermissionInfo>() {
- @Override
- public UsesPermissionInfo createFromParcel(Parcel source) {
- return new UsesPermissionInfo(source);
- }
- @Override
- public UsesPermissionInfo[] newArray(int size) {
- return new UsesPermissionInfo[size];
- }
- };
-}
diff --git a/core/java/android/content/res/AssetManager.java b/core/java/android/content/res/AssetManager.java
index 9e0a9ba0dc7b..faf17e011b23 100644
--- a/core/java/android/content/res/AssetManager.java
+++ b/core/java/android/content/res/AssetManager.java
@@ -1051,6 +1051,14 @@ public final class AssetManager implements AutoCloseable {
}
}
+ int[] getAttributeResolutionStack(long themePtr, @AttrRes int defStyleAttr,
+ @StyleRes int defStyleRes, @StyleRes int xmlStyle) {
+ synchronized (this) {
+ return nativeAttributeResolutionStack(
+ mObject, themePtr, xmlStyle, defStyleAttr, defStyleRes);
+ }
+ }
+
@UnsupportedAppUsage
boolean resolveAttrs(long themePtr, @AttrRes int defStyleAttr, @StyleRes int defStyleRes,
@Nullable int[] inValues, @NonNull int[] inAttrs, @NonNull int[] outValues,
@@ -1419,6 +1427,8 @@ public final class AssetManager implements AutoCloseable {
private static native @Nullable String nativeGetLastResourceResolution(long ptr);
// Style attribute retrieval native methods.
+ private static native int[] nativeAttributeResolutionStack(long ptr, long themePtr,
+ @StyleRes int xmlStyleRes, @AttrRes int defStyleAttr, @StyleRes int defStyleRes);
private static native void nativeApplyStyle(long ptr, long themePtr, @AttrRes int defStyleAttr,
@StyleRes int defStyleRes, long xmlParserPtr, @NonNull int[] inAttrs,
long outValuesAddress, long outIndicesAddress);
diff --git a/core/java/android/content/res/Resources.java b/core/java/android/content/res/Resources.java
index 59db49e0d37e..a2ae994f7b0f 100644
--- a/core/java/android/content/res/Resources.java
+++ b/core/java/android/content/res/Resources.java
@@ -1725,6 +1725,68 @@ public class Resources {
public void rebase() {
mThemeImpl.rebase();
}
+
+ /**
+ * Returns the resource ID for the style specified using {@code style="..."} in the
+ * {@link AttributeSet}'s backing XML element or {@link Resources#ID_NULL} otherwise if not
+ * specified or otherwise not applicable.
+ * <p>
+ * Each {@link android.view.View} can have an explicit style specified in the layout file.
+ * This style is used first during the {@link android.view.View} attribute resolution, then
+ * if an attribute is not defined there the resource system looks at default style and theme
+ * as fallbacks.
+ *
+ * @param set The base set of attribute values.
+ *
+ * @return The resource ID for the style specified using {@code style="..."} in the
+ * {@link AttributeSet}'s backing XML element or {@link Resources#ID_NULL} otherwise
+ * if not specified or otherwise not applicable.
+ */
+ @StyleRes
+ public int getExplicitStyle(@Nullable AttributeSet set) {
+ if (set == null) {
+ return ID_NULL;
+ }
+ int styleAttr = set.getStyleAttribute();
+ if (styleAttr == ID_NULL) {
+ return ID_NULL;
+ }
+ String styleAttrType = getResources().getResourceTypeName(styleAttr);
+ if ("attr".equals(styleAttrType)) {
+ TypedValue explicitStyle = new TypedValue();
+ boolean resolved = resolveAttribute(styleAttr, explicitStyle, true);
+ if (resolved) {
+ return explicitStyle.resourceId;
+ }
+ } else if ("style".equals(styleAttrType)) {
+ return styleAttr;
+ }
+ return ID_NULL;
+ }
+
+ /**
+ * Returns the ordered list of resource ID that are considered when resolving attribute
+ * values when making an equivalent call to
+ * {@link #obtainStyledAttributes(AttributeSet, int[], int, int)} . The list will include
+ * a set of explicit styles ({@code explicitStyleRes} and it will include the default styles
+ * ({@code defStyleAttr} and {@code defStyleRes}).
+ *
+ * @param defStyleAttr An attribute in the current theme that contains a
+ * reference to a style resource that supplies
+ * defaults values for the TypedArray. Can be
+ * 0 to not look for defaults.
+ * @param defStyleRes A resource identifier of a style resource that
+ * supplies default values for the TypedArray,
+ * used only if defStyleAttr is 0 or can not be found
+ * in the theme. Can be 0 to not look for defaults.
+ * @param explicitStyleRes A resource identifier of an explicit style resource.
+ * @return ordered list of resource ID that are considered when resolving attribute values.
+ */
+ public int[] getAttributeResolutionStack(@AttrRes int defStyleAttr,
+ @StyleRes int defStyleRes, @StyleRes int explicitStyleRes) {
+ return mThemeImpl.getAttributeResolutionStack(
+ defStyleAttr, defStyleRes, explicitStyleRes);
+ }
}
static class ThemeKey implements Cloneable {
diff --git a/core/java/android/content/res/ResourcesImpl.java b/core/java/android/content/res/ResourcesImpl.java
index 98980799a365..da064c956fcc 100644
--- a/core/java/android/content/res/ResourcesImpl.java
+++ b/core/java/android/content/res/ResourcesImpl.java
@@ -1488,6 +1488,32 @@ public class ResourcesImpl {
}
}
}
+
+ /**
+ * Returns the ordered list of resource ID that are considered when resolving attribute
+ * values when making an equivalent call to
+ * {@link #obtainStyledAttributes(Resources.Theme, AttributeSet, int[], int, int)}. The list
+ * will include a set of explicit styles ({@code explicitStyleRes} and it will include the
+ * default styles ({@code defStyleAttr} and {@code defStyleRes}).
+ *
+ * @param defStyleAttr An attribute in the current theme that contains a
+ * reference to a style resource that supplies
+ * defaults values for the TypedArray. Can be
+ * 0 to not look for defaults.
+ * @param defStyleRes A resource identifier of a style resource that
+ * supplies default values for the TypedArray,
+ * used only if defStyleAttr is 0 or can not be found
+ * in the theme. Can be 0 to not look for defaults.
+ * @param explicitStyleRes A resource identifier of an explicit style resource.
+ * @return ordered list of resource ID that are considered when resolving attribute values.
+ */
+ public int[] getAttributeResolutionStack(@AttrRes int defStyleAttr,
+ @StyleRes int defStyleRes, @StyleRes int explicitStyleRes) {
+ synchronized (mKey) {
+ return mAssets.getAttributeResolutionStack(
+ mTheme, defStyleAttr, defStyleRes, explicitStyleRes);
+ }
+ }
}
private static class LookupStack {
diff --git a/core/java/android/hardware/camera2/CameraCharacteristics.java b/core/java/android/hardware/camera2/CameraCharacteristics.java
index 1881a0cd32e8..0e4ff78af1e0 100644
--- a/core/java/android/hardware/camera2/CameraCharacteristics.java
+++ b/core/java/android/hardware/camera2/CameraCharacteristics.java
@@ -1159,9 +1159,10 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri
* <li>Each output JPEG size in android.scaler.availableStreamConfigurations will have at least
* one corresponding size that has the same aspect ratio in availableThumbnailSizes,
* and vice versa.</li>
- * <li>All non-<code>(0, 0)</code> sizes will have non-zero widths and heights.
- * This key is available on all devices.</li>
+ * <li>All non-<code>(0, 0)</code> sizes will have non-zero widths and heights.</li>
* </ul>
+ * <p>This list is also used as supported thumbnail sizes for HEIC image format capture.</p>
+ * <p>This key is available on all devices.</p>
*
* @see CaptureRequest#JPEG_THUMBNAIL_SIZE
*/
@@ -3838,6 +3839,74 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri
public static final Key<int[]> DISTORTION_CORRECTION_AVAILABLE_MODES =
new Key<int[]>("android.distortionCorrection.availableModes", int[].class);
+ /**
+ * <p>The available HEIC (ISO/IEC 23008-12) stream
+ * configurations that this camera device supports
+ * (i.e. format, width, height, output/input stream).</p>
+ * <p>The configurations are listed as <code>(format, width, height, input?)</code> tuples.</p>
+ * <p>If the camera device supports HEIC image format, it will support identical set of stream
+ * combinations involving HEIC image format, compared to the combinations involving JPEG
+ * image format as required by the device's hardware level and capabilities.</p>
+ * <p>All the static, control, and dynamic metadata tags related to JPEG apply to HEIC formats.
+ * Configuring JPEG and HEIC streams at the same time is not supported.</p>
+ * <p><b>Optional</b> - This value may be {@code null} on some devices.</p>
+ * <p><b>Limited capability</b> -
+ * Present on all camera devices that report being at least {@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL_LIMITED HARDWARE_LEVEL_LIMITED} devices in the
+ * {@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL android.info.supportedHardwareLevel} key</p>
+ *
+ * @see CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL
+ * @hide
+ */
+ public static final Key<android.hardware.camera2.params.StreamConfiguration[]> HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS =
+ new Key<android.hardware.camera2.params.StreamConfiguration[]>("android.heic.availableHeicStreamConfigurations", android.hardware.camera2.params.StreamConfiguration[].class);
+
+ /**
+ * <p>This lists the minimum frame duration for each
+ * format/size combination for HEIC output formats.</p>
+ * <p>This should correspond to the frame duration when only that
+ * stream is active, with all processing (typically in android.*.mode)
+ * set to either OFF or FAST.</p>
+ * <p>When multiple streams are used in a request, the minimum frame
+ * duration will be max(individual stream min durations).</p>
+ * <p>See {@link CaptureRequest#SENSOR_FRAME_DURATION android.sensor.frameDuration} and
+ * android.scaler.availableStallDurations for more details about
+ * calculating the max frame rate.</p>
+ * <p><b>Units</b>: (format, width, height, ns) x n</p>
+ * <p><b>Optional</b> - This value may be {@code null} on some devices.</p>
+ * <p><b>Limited capability</b> -
+ * Present on all camera devices that report being at least {@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL_LIMITED HARDWARE_LEVEL_LIMITED} devices in the
+ * {@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL android.info.supportedHardwareLevel} key</p>
+ *
+ * @see CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL
+ * @see CaptureRequest#SENSOR_FRAME_DURATION
+ * @hide
+ */
+ public static final Key<android.hardware.camera2.params.StreamConfigurationDuration[]> HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS =
+ new Key<android.hardware.camera2.params.StreamConfigurationDuration[]>("android.heic.availableHeicMinFrameDurations", android.hardware.camera2.params.StreamConfigurationDuration[].class);
+
+ /**
+ * <p>This lists the maximum stall duration for each
+ * output format/size combination for HEIC streams.</p>
+ * <p>A stall duration is how much extra time would get added
+ * to the normal minimum frame duration for a repeating request
+ * that has streams with non-zero stall.</p>
+ * <p>This functions similarly to
+ * android.scaler.availableStallDurations for HEIC
+ * streams.</p>
+ * <p>All HEIC output stream formats may have a nonzero stall
+ * duration.</p>
+ * <p><b>Units</b>: (format, width, height, ns) x n</p>
+ * <p><b>Optional</b> - This value may be {@code null} on some devices.</p>
+ * <p><b>Limited capability</b> -
+ * Present on all camera devices that report being at least {@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL_LIMITED HARDWARE_LEVEL_LIMITED} devices in the
+ * {@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL android.info.supportedHardwareLevel} key</p>
+ *
+ * @see CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL
+ * @hide
+ */
+ public static final Key<android.hardware.camera2.params.StreamConfigurationDuration[]> HEIC_AVAILABLE_HEIC_STALL_DURATIONS =
+ new Key<android.hardware.camera2.params.StreamConfigurationDuration[]>("android.heic.availableHeicStallDurations", android.hardware.camera2.params.StreamConfigurationDuration[].class);
+
/*~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~
* End generated code
*~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~O@*/
diff --git a/core/java/android/hardware/camera2/CameraDevice.java b/core/java/android/hardware/camera2/CameraDevice.java
index 9c213f2f27a5..20fc53fee2e6 100644
--- a/core/java/android/hardware/camera2/CameraDevice.java
+++ b/core/java/android/hardware/camera2/CameraDevice.java
@@ -356,12 +356,6 @@ public abstract class CameraDevice implements AutoCloseable {
* </table><br>
* </p>
*
- * <p>MONOCHROME-capability ({@link CameraCharacteristics#REQUEST_AVAILABLE_CAPABILITIES}
- * includes {@link CameraMetadata#REQUEST_AVAILABLE_CAPABILITIES_MONOCHROME MONOCHROME}) devices
- * supporting {@link android.graphics.ImageFormat#Y8 Y8} support substituting {@code YUV}
- * streams with {@code Y8} in all guaranteed stream combinations for the device's hardware level
- * and capabilities.</p>
- *
* <p>FULL-level ({@link CameraCharacteristics#INFO_SUPPORTED_HARDWARE_LEVEL}
* {@code == }{@link CameraMetadata#INFO_SUPPORTED_HARDWARE_LEVEL_FULL FULL}) devices
* support at least the following stream combinations in addition to those for
@@ -435,6 +429,18 @@ public abstract class CameraDevice implements AutoCloseable {
* </table><br>
* </p>
*
+ * <p>MONOCHROME-capability ({@link CameraCharacteristics#REQUEST_AVAILABLE_CAPABILITIES}
+ * includes {@link CameraMetadata#REQUEST_AVAILABLE_CAPABILITIES_MONOCHROME MONOCHROME}) devices
+ * supporting {@link android.graphics.ImageFormat#Y8 Y8} support substituting {@code YUV}
+ * streams with {@code Y8} in all guaranteed stream combinations for the device's hardware level
+ * and capabilities.</p>
+ *
+ * <p>Devices capable of outputting HEIC formats ({@link StreamConfigurationMap#getOutputFormats}
+ * contains {@link android.graphics.ImageFormat#HEIC}) will support substituting {@code JPEG}
+ * streams with {@code HEIC} in all guaranteed stream combinations for the device's hardware
+ * level and capabilities. Calling createCaptureSession with both JPEG and HEIC outputs is not
+ * supported.</p>
+ *
* <p>Clients can access the above mandatory stream combination tables via
* {@link android.hardware.camera2.params.MandatoryStreamCombination}.</p>
*
diff --git a/core/java/android/hardware/camera2/CaptureRequest.java b/core/java/android/hardware/camera2/CaptureRequest.java
index 3d3a916bae7a..525070103c2c 100644
--- a/core/java/android/hardware/camera2/CaptureRequest.java
+++ b/core/java/android/hardware/camera2/CaptureRequest.java
@@ -2126,6 +2126,7 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
* <p>Setting a location object in a request will include the GPS coordinates of the location
* into any JPEG images captured based on the request. These coordinates can then be
* viewed by anyone who receives the JPEG image.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p>This key is available on all devices.</p>
*/
@PublicKey
@@ -2136,6 +2137,7 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
/**
* <p>GPS coordinates to include in output JPEG
* EXIF.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p><b>Range of valid values:</b><br>
* (-180 - 180], [-90,90], [-inf, inf]</p>
* <p>This key is available on all devices.</p>
@@ -2147,6 +2149,7 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
/**
* <p>32 characters describing GPS algorithm to
* include in EXIF.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p>This key is available on all devices.</p>
* @hide
*/
@@ -2156,6 +2159,7 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
/**
* <p>Time GPS fix was made to include in
* EXIF.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p><b>Units</b>: UTC in seconds since January 1, 1970</p>
* <p>This key is available on all devices.</p>
* @hide
@@ -2195,6 +2199,10 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
* </code></pre>
* <p>For EXTERNAL cameras the sensor orientation will always be set to 0 and the facing will
* also be set to EXTERNAL. The above code is not relevant in such case.</p>
+ * <p>This tag is also used to describe the orientation of the HEIC image capture, in which
+ * case the rotation is reflected by
+ * {@link android.media.ExifInterface#TAG_ORIENTATION EXIF orientation flag}, and not by
+ * rotating the image data itself.</p>
* <p><b>Units</b>: Degrees in multiples of 90</p>
* <p><b>Range of valid values:</b><br>
* 0, 90, 180, 270</p>
@@ -2209,7 +2217,8 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
/**
* <p>Compression quality of the final JPEG
* image.</p>
- * <p>85-95 is typical usage range.</p>
+ * <p>85-95 is typical usage range. This tag is also used to describe the quality
+ * of the HEIC image capture.</p>
* <p><b>Range of valid values:</b><br>
* 1-100; larger is higher quality</p>
* <p>This key is available on all devices.</p>
@@ -2221,6 +2230,7 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
/**
* <p>Compression quality of JPEG
* thumbnail.</p>
+ * <p>This tag is also used to describe the quality of the HEIC image capture.</p>
* <p><b>Range of valid values:</b><br>
* 1-100; larger is higher quality</p>
* <p>This key is available on all devices.</p>
@@ -2253,6 +2263,10 @@ public final class CaptureRequest extends CameraMetadata<CaptureRequest.Key<?>>
* orientation is requested. LEGACY device will always report unrotated thumbnail
* size.</li>
* </ul>
+ * <p>The tag is also used as thumbnail size for HEIC image format capture, in which case the
+ * the thumbnail rotation is reflected by
+ * {@link android.media.ExifInterface#TAG_ORIENTATION EXIF orientation flag}, and not by
+ * rotating the thumbnail data itself.</p>
* <p><b>Range of valid values:</b><br>
* {@link CameraCharacteristics#JPEG_AVAILABLE_THUMBNAIL_SIZES android.jpeg.availableThumbnailSizes}</p>
* <p>This key is available on all devices.</p>
diff --git a/core/java/android/hardware/camera2/CaptureResult.java b/core/java/android/hardware/camera2/CaptureResult.java
index 8982b40be29b..13ad092f6efd 100644
--- a/core/java/android/hardware/camera2/CaptureResult.java
+++ b/core/java/android/hardware/camera2/CaptureResult.java
@@ -2450,6 +2450,7 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
* <p>Setting a location object in a request will include the GPS coordinates of the location
* into any JPEG images captured based on the request. These coordinates can then be
* viewed by anyone who receives the JPEG image.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p>This key is available on all devices.</p>
*/
@PublicKey
@@ -2460,6 +2461,7 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
/**
* <p>GPS coordinates to include in output JPEG
* EXIF.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p><b>Range of valid values:</b><br>
* (-180 - 180], [-90,90], [-inf, inf]</p>
* <p>This key is available on all devices.</p>
@@ -2471,6 +2473,7 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
/**
* <p>32 characters describing GPS algorithm to
* include in EXIF.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p>This key is available on all devices.</p>
* @hide
*/
@@ -2480,6 +2483,7 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
/**
* <p>Time GPS fix was made to include in
* EXIF.</p>
+ * <p>This tag is also used for HEIC image capture.</p>
* <p><b>Units</b>: UTC in seconds since January 1, 1970</p>
* <p>This key is available on all devices.</p>
* @hide
@@ -2519,6 +2523,10 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
* </code></pre>
* <p>For EXTERNAL cameras the sensor orientation will always be set to 0 and the facing will
* also be set to EXTERNAL. The above code is not relevant in such case.</p>
+ * <p>This tag is also used to describe the orientation of the HEIC image capture, in which
+ * case the rotation is reflected by
+ * {@link android.media.ExifInterface#TAG_ORIENTATION EXIF orientation flag}, and not by
+ * rotating the image data itself.</p>
* <p><b>Units</b>: Degrees in multiples of 90</p>
* <p><b>Range of valid values:</b><br>
* 0, 90, 180, 270</p>
@@ -2533,7 +2541,8 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
/**
* <p>Compression quality of the final JPEG
* image.</p>
- * <p>85-95 is typical usage range.</p>
+ * <p>85-95 is typical usage range. This tag is also used to describe the quality
+ * of the HEIC image capture.</p>
* <p><b>Range of valid values:</b><br>
* 1-100; larger is higher quality</p>
* <p>This key is available on all devices.</p>
@@ -2545,6 +2554,7 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
/**
* <p>Compression quality of JPEG
* thumbnail.</p>
+ * <p>This tag is also used to describe the quality of the HEIC image capture.</p>
* <p><b>Range of valid values:</b><br>
* 1-100; larger is higher quality</p>
* <p>This key is available on all devices.</p>
@@ -2577,6 +2587,10 @@ public class CaptureResult extends CameraMetadata<CaptureResult.Key<?>> {
* orientation is requested. LEGACY device will always report unrotated thumbnail
* size.</li>
* </ul>
+ * <p>The tag is also used as thumbnail size for HEIC image format capture, in which case the
+ * the thumbnail rotation is reflected by
+ * {@link android.media.ExifInterface#TAG_ORIENTATION EXIF orientation flag}, and not by
+ * rotating the thumbnail data itself.</p>
* <p><b>Range of valid values:</b><br>
* {@link CameraCharacteristics#JPEG_AVAILABLE_THUMBNAIL_SIZES android.jpeg.availableThumbnailSizes}</p>
* <p>This key is available on all devices.</p>
diff --git a/core/java/android/hardware/camera2/impl/CameraMetadataNative.java b/core/java/android/hardware/camera2/impl/CameraMetadataNative.java
index 7877a4d51313..65026b6feb9f 100644
--- a/core/java/android/hardware/camera2/impl/CameraMetadataNative.java
+++ b/core/java/android/hardware/camera2/impl/CameraMetadataNative.java
@@ -1133,6 +1133,9 @@ public class CameraMetadataNative implements Parcelable {
/*dynamicDepthConfigurations*/ null,
/*dynamicDepthMinFrameDurations*/ null,
/*dynamicDepthStallDurations*/ null,
+ /*heicconfiguration*/ null,
+ /*heicminduration*/ null,
+ /*heicstallduration*/ null,
/*highspeedvideoconfigurations*/ null,
/*inputoutputformatsmap*/ null, listHighResolution, supportsPrivate[i]);
break;
@@ -1144,6 +1147,9 @@ public class CameraMetadataNative implements Parcelable {
/*dynamicDepthConfigurations*/ null,
/*dynamicDepthMinFrameDurations*/ null,
/*dynamicDepthStallDurations*/ null,
+ /*heicconfiguration*/ null,
+ /*heicminduration*/ null,
+ /*heicstallduration*/ null,
highSpeedVideoConfigurations,
/*inputoutputformatsmap*/ null, listHighResolution, supportsPrivate[i]);
break;
@@ -1155,6 +1161,9 @@ public class CameraMetadataNative implements Parcelable {
/*dynamicDepthConfigurations*/ null,
/*dynamicDepthMinFrameDurations*/ null,
/*dynamicDepthStallDurations*/ null,
+ /*heicconfiguration*/ null,
+ /*heicminduration*/ null,
+ /*heicstallduration*/ null,
/*highSpeedVideoConfigurations*/ null,
inputOutputFormatsMap, listHighResolution, supportsPrivate[i]);
break;
@@ -1166,6 +1175,9 @@ public class CameraMetadataNative implements Parcelable {
/*dynamicDepthConfigurations*/ null,
/*dynamicDepthMinFrameDurations*/ null,
/*dynamicDepthStallDurations*/ null,
+ /*heicconfiguration*/ null,
+ /*heicminduration*/ null,
+ /*heicstallduration*/ null,
/*highSpeedVideoConfigurations*/ null,
/*inputOutputFormatsMap*/ null, listHighResolution, supportsPrivate[i]);
}
@@ -1230,6 +1242,12 @@ public class CameraMetadataNative implements Parcelable {
CameraCharacteristics.DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS);
StreamConfigurationDuration[] dynamicDepthStallDurations = getBase(
CameraCharacteristics.DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS);
+ StreamConfiguration[] heicConfigurations = getBase(
+ CameraCharacteristics.HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS);
+ StreamConfigurationDuration[] heicMinFrameDurations = getBase(
+ CameraCharacteristics.HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS);
+ StreamConfigurationDuration[] heicStallDurations = getBase(
+ CameraCharacteristics.HEIC_AVAILABLE_HEIC_STALL_DURATIONS);
HighSpeedVideoConfiguration[] highSpeedVideoConfigurations = getBase(
CameraCharacteristics.CONTROL_AVAILABLE_HIGH_SPEED_VIDEO_CONFIGURATIONS);
ReprocessFormatsMap inputOutputFormatsMap = getBase(
@@ -1239,7 +1257,9 @@ public class CameraMetadataNative implements Parcelable {
configurations, minFrameDurations, stallDurations,
depthConfigurations, depthMinFrameDurations, depthStallDurations,
dynamicDepthConfigurations, dynamicDepthMinFrameDurations,
- dynamicDepthStallDurations, highSpeedVideoConfigurations, inputOutputFormatsMap,
+ dynamicDepthStallDurations, heicConfigurations,
+ heicMinFrameDurations, heicStallDurations,
+ highSpeedVideoConfigurations, inputOutputFormatsMap,
listHighResolution);
}
diff --git a/core/java/android/hardware/camera2/params/StreamConfigurationMap.java b/core/java/android/hardware/camera2/params/StreamConfigurationMap.java
index a22e008a65fd..996f9978a612 100644
--- a/core/java/android/hardware/camera2/params/StreamConfigurationMap.java
+++ b/core/java/android/hardware/camera2/params/StreamConfigurationMap.java
@@ -79,6 +79,22 @@ public final class StreamConfigurationMap {
* @param configurations a non-{@code null} array of {@link StreamConfiguration}
* @param minFrameDurations a non-{@code null} array of {@link StreamConfigurationDuration}
* @param stallDurations a non-{@code null} array of {@link StreamConfigurationDuration}
+ * @param depthConfigurations a non-{@code null} array of depth {@link StreamConfiguration}
+ * @param depthMinFrameDurations a non-{@code null} array of depth
+ * {@link StreamConfigurationDuration}
+ * @param depthStallDurations a non-{@code null} array of depth
+ * {@link StreamConfigurationDuration}
+ * @param dynamicDepthConfigurations a non-{@code null} array of dynamic depth
+ * {@link StreamConfiguration}
+ * @param dynamicDepthMinFrameDurations a non-{@code null} array of dynamic depth
+ * {@link StreamConfigurationDuration}
+ * @param dynamicDepthStallDurations a non-{@code null} array of dynamic depth
+ * {@link StreamConfigurationDuration}
+ * @param heicConfigurations a non-{@code null} array of heic {@link StreamConfiguration}
+ * @param heicMinFrameDurations a non-{@code null} array of heic
+ * {@link StreamConfigurationDuration}
+ * @param heicStallDurations a non-{@code null} array of heic
+ * {@link StreamConfigurationDuration}
* @param highSpeedVideoConfigurations an array of {@link HighSpeedVideoConfiguration}, null if
* camera device does not support high speed video recording
* @param listHighResolution a flag indicating whether the device supports BURST_CAPTURE
@@ -98,14 +114,19 @@ public final class StreamConfigurationMap {
StreamConfiguration[] dynamicDepthConfigurations,
StreamConfigurationDuration[] dynamicDepthMinFrameDurations,
StreamConfigurationDuration[] dynamicDepthStallDurations,
+ StreamConfiguration[] heicConfigurations,
+ StreamConfigurationDuration[] heicMinFrameDurations,
+ StreamConfigurationDuration[] heicStallDurations,
HighSpeedVideoConfiguration[] highSpeedVideoConfigurations,
ReprocessFormatsMap inputOutputFormatsMap,
boolean listHighResolution) {
this(configurations, minFrameDurations, stallDurations,
depthConfigurations, depthMinFrameDurations, depthStallDurations,
dynamicDepthConfigurations, dynamicDepthMinFrameDurations,
- dynamicDepthStallDurations, highSpeedVideoConfigurations, inputOutputFormatsMap,
- listHighResolution, /*enforceImplementationDefined*/ true);
+ dynamicDepthStallDurations,
+ heicConfigurations, heicMinFrameDurations, heicStallDurations,
+ highSpeedVideoConfigurations, inputOutputFormatsMap, listHighResolution,
+ /*enforceImplementationDefined*/ true);
}
/**
@@ -117,6 +138,22 @@ public final class StreamConfigurationMap {
* @param configurations a non-{@code null} array of {@link StreamConfiguration}
* @param minFrameDurations a non-{@code null} array of {@link StreamConfigurationDuration}
* @param stallDurations a non-{@code null} array of {@link StreamConfigurationDuration}
+ * @param depthConfigurations a non-{@code null} array of depth {@link StreamConfiguration}
+ * @param depthMinFrameDurations a non-{@code null} array of depth
+ * {@link StreamConfigurationDuration}
+ * @param depthStallDurations a non-{@code null} array of depth
+ * {@link StreamConfigurationDuration}
+ * @param dynamicDepthConfigurations a non-{@code null} array of dynamic depth
+ * {@link StreamConfiguration}
+ * @param dynamicDepthMinFrameDurations a non-{@code null} array of dynamic depth
+ * {@link StreamConfigurationDuration}
+ * @param dynamicDepthStallDurations a non-{@code null} array of dynamic depth
+ * {@link StreamConfigurationDuration}
+ * @param heicConfigurations a non-{@code null} array of heic {@link StreamConfiguration}
+ * @param heicMinFrameDurations a non-{@code null} array of heic
+ * {@link StreamConfigurationDuration}
+ * @param heicStallDurations a non-{@code null} array of heic
+ * {@link StreamConfigurationDuration}
* @param highSpeedVideoConfigurations an array of {@link HighSpeedVideoConfiguration}, null if
* camera device does not support high speed video recording
* @param listHighResolution a flag indicating whether the device supports BURST_CAPTURE
@@ -138,14 +175,23 @@ public final class StreamConfigurationMap {
StreamConfiguration[] dynamicDepthConfigurations,
StreamConfigurationDuration[] dynamicDepthMinFrameDurations,
StreamConfigurationDuration[] dynamicDepthStallDurations,
+ StreamConfiguration[] heicConfigurations,
+ StreamConfigurationDuration[] heicMinFrameDurations,
+ StreamConfigurationDuration[] heicStallDurations,
HighSpeedVideoConfiguration[] highSpeedVideoConfigurations,
ReprocessFormatsMap inputOutputFormatsMap,
boolean listHighResolution,
boolean enforceImplementationDefined) {
+ if (configurations == null &&
+ depthConfigurations == null &&
+ heicConfigurations == null) {
+ throw new NullPointerException("At least one of color/depth/heic configurations " +
+ "must not be null");
+ }
+
if (configurations == null) {
// If no color configurations exist, ensure depth ones do
- checkArrayElementsNotNull(depthConfigurations, "depthConfigurations");
mConfigurations = new StreamConfiguration[0];
mMinFrameDurations = new StreamConfigurationDuration[0];
mStallDurations = new StreamConfigurationDuration[0];
@@ -183,6 +229,19 @@ public final class StreamConfigurationMap {
"dynamicDepthStallDurations");
}
+ if (heicConfigurations == null) {
+ mHeicConfigurations = new StreamConfiguration[0];
+ mHeicMinFrameDurations = new StreamConfigurationDuration[0];
+ mHeicStallDurations = new StreamConfigurationDuration[0];
+ } else {
+ mHeicConfigurations = checkArrayElementsNotNull(heicConfigurations,
+ "heicConfigurations");
+ mHeicMinFrameDurations = checkArrayElementsNotNull(heicMinFrameDurations,
+ "heicMinFrameDurations");
+ mHeicStallDurations = checkArrayElementsNotNull(heicStallDurations,
+ "heicStallDurations");
+ }
+
if (highSpeedVideoConfigurations == null) {
mHighSpeedVideoConfigurations = new HighSpeedVideoConfiguration[0];
} else {
@@ -235,6 +294,17 @@ public final class StreamConfigurationMap {
mDynamicDepthOutputFormats.get(config.getFormat()) + 1);
}
+ // For each heic format, track how many sizes there are available to configure
+ for (StreamConfiguration config : mHeicConfigurations) {
+ if (!config.isOutput()) {
+ // Ignoring input depth configs
+ continue;
+ }
+
+ mHeicOutputFormats.put(config.getFormat(),
+ mHeicOutputFormats.get(config.getFormat()) + 1);
+ }
+
if (configurations != null && enforceImplementationDefined &&
mOutputFormats.indexOfKey(HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED) < 0) {
throw new AssertionError(
@@ -302,7 +372,16 @@ public final class StreamConfigurationMap {
if (mInputOutputFormatsMap == null) {
return new int[0];
}
- return mInputOutputFormatsMap.getOutputs(inputFormat);
+
+ int[] outputs = mInputOutputFormatsMap.getOutputs(inputFormat);
+ if (mHeicOutputFormats.size() > 0) {
+ // All reprocessing formats map contain JPEG.
+ int[] outputsWithHeic = Arrays.copyOf(outputs, outputs.length+1);
+ outputsWithHeic[outputs.length] = ImageFormat.HEIC;
+ return outputsWithHeic;
+ } else {
+ return outputs;
+ }
}
/**
@@ -366,6 +445,8 @@ public final class StreamConfigurationMap {
return mDepthOutputFormats.indexOfKey(internalFormat) >= 0;
} else if (dataspace == HAL_DATASPACE_DYNAMIC_DEPTH) {
return mDynamicDepthOutputFormats.indexOfKey(internalFormat) >= 0;
+ } else if (dataspace == HAL_DATASPACE_HEIF) {
+ return mHeicOutputFormats.indexOfKey(internalFormat) >= 0;
} else {
return getFormatsMap(/*output*/true).indexOfKey(internalFormat) >= 0;
}
@@ -479,6 +560,7 @@ public final class StreamConfigurationMap {
StreamConfiguration[] configs =
surfaceDataspace == HAL_DATASPACE_DEPTH ? mDepthConfigurations :
surfaceDataspace == HAL_DATASPACE_DYNAMIC_DEPTH ? mDynamicDepthConfigurations :
+ surfaceDataspace == HAL_DATASPACE_HEIF ? mHeicConfigurations :
mConfigurations;
for (StreamConfiguration config : configs) {
if (config.getFormat() == surfaceFormat && config.isOutput()) {
@@ -512,9 +594,10 @@ public final class StreamConfigurationMap {
int dataspace = imageFormatToDataspace(format);
StreamConfiguration[] configs =
- dataspace == HAL_DATASPACE_DEPTH ? mDepthConfigurations :
- dataspace == HAL_DATASPACE_DYNAMIC_DEPTH ? mDynamicDepthConfigurations :
- mConfigurations;
+ dataspace == HAL_DATASPACE_DEPTH ? mDepthConfigurations :
+ dataspace == HAL_DATASPACE_DYNAMIC_DEPTH ? mDynamicDepthConfigurations :
+ dataspace == HAL_DATASPACE_HEIF ? mHeicConfigurations :
+ mConfigurations;
for (StreamConfiguration config : configs) {
if ((config.getFormat() == internalFormat) && config.isOutput() &&
config.getSize().equals(size)) {
@@ -1033,6 +1116,9 @@ public final class StreamConfigurationMap {
Arrays.equals(mDynamicDepthMinFrameDurations,
other.mDynamicDepthMinFrameDurations) &&
Arrays.equals(mDynamicDepthStallDurations, other.mDynamicDepthStallDurations) &&
+ Arrays.equals(mHeicConfigurations, other.mHeicConfigurations) &&
+ Arrays.equals(mHeicMinFrameDurations, other.mHeicMinFrameDurations) &&
+ Arrays.equals(mHeicStallDurations, other.mHeicStallDurations) &&
Arrays.equals(mHighSpeedVideoConfigurations,
other.mHighSpeedVideoConfigurations);
}
@@ -1049,7 +1135,9 @@ public final class StreamConfigurationMap {
mConfigurations, mMinFrameDurations, mStallDurations,
mDepthConfigurations, mDepthMinFrameDurations, mDepthStallDurations,
mDynamicDepthConfigurations, mDynamicDepthMinFrameDurations,
- mDynamicDepthStallDurations, mHighSpeedVideoConfigurations);
+ mDynamicDepthStallDurations, mHeicConfigurations,
+ mHeicMinFrameDurations, mHeicStallDurations,
+ mHighSpeedVideoConfigurations);
}
// Check that the argument is supported by #getOutputFormats or #getInputFormats
@@ -1068,6 +1156,10 @@ public final class StreamConfigurationMap {
if (mDynamicDepthOutputFormats.indexOfKey(internalFormat) >= 0) {
return format;
}
+ } else if (internalDataspace == HAL_DATASPACE_HEIF) {
+ if (mHeicOutputFormats.indexOfKey(internalFormat) >= 0) {
+ return format;
+ }
} else {
if (mAllOutputFormats.indexOfKey(internalFormat) >= 0) {
return format;
@@ -1108,8 +1200,9 @@ public final class StreamConfigurationMap {
case HAL_PIXEL_FORMAT_Y16:
return format;
case ImageFormat.JPEG:
+ case ImageFormat.HEIC:
throw new IllegalArgumentException(
- "ImageFormat.JPEG is an unknown internal format");
+ "An unknown internal format: " + format);
default:
return checkArgumentFormat(format);
}
@@ -1267,6 +1360,8 @@ public final class StreamConfigurationMap {
* <ul>
* <li>ImageFormat.JPEG => HAL_PIXEL_FORMAT_BLOB
* <li>ImageFormat.DEPTH_POINT_CLOUD => HAL_PIXEL_FORMAT_BLOB
+ * <li>ImageFormat.DEPTH_JPEG => HAL_PIXEL_FORMAT_BLOB
+ * <li>ImageFormat.HEIC => HAL_PIXEL_FORMAT_BLOB
* <li>ImageFormat.DEPTH16 => HAL_PIXEL_FORMAT_Y16
* </ul>
* </p>
@@ -1292,6 +1387,7 @@ public final class StreamConfigurationMap {
case ImageFormat.JPEG:
case ImageFormat.DEPTH_POINT_CLOUD:
case ImageFormat.DEPTH_JPEG:
+ case ImageFormat.HEIC:
return HAL_PIXEL_FORMAT_BLOB;
case ImageFormat.DEPTH16:
return HAL_PIXEL_FORMAT_Y16;
@@ -1312,6 +1408,7 @@ public final class StreamConfigurationMap {
* <li>ImageFormat.DEPTH_POINT_CLOUD => HAL_DATASPACE_DEPTH
* <li>ImageFormat.DEPTH16 => HAL_DATASPACE_DEPTH
* <li>ImageFormat.DEPTH_JPEG => HAL_DATASPACE_DYNAMIC_DEPTH
+ * <li>ImageFormat.HEIC => HAL_DATASPACE_HEIF
* <li>others => HAL_DATASPACE_UNKNOWN
* </ul>
* </p>
@@ -1343,6 +1440,8 @@ public final class StreamConfigurationMap {
return HAL_DATASPACE_DEPTH;
case ImageFormat.DEPTH_JPEG:
return HAL_DATASPACE_DYNAMIC_DEPTH;
+ case ImageFormat.HEIC:
+ return HAL_DATASPACE_HEIF;
default:
return HAL_DATASPACE_UNKNOWN;
}
@@ -1394,14 +1493,17 @@ public final class StreamConfigurationMap {
!output ? mInputFormats :
dataspace == HAL_DATASPACE_DEPTH ? mDepthOutputFormats :
dataspace == HAL_DATASPACE_DYNAMIC_DEPTH ? mDynamicDepthOutputFormats :
+ dataspace == HAL_DATASPACE_HEIF ? mHeicOutputFormats :
highRes ? mHighResOutputFormats :
mOutputFormats;
int sizesCount = formatsMap.get(format);
if ( ((!output || (dataspace == HAL_DATASPACE_DEPTH ||
- dataspace == HAL_DATASPACE_DYNAMIC_DEPTH)) && sizesCount == 0) ||
+ dataspace == HAL_DATASPACE_DYNAMIC_DEPTH ||
+ dataspace == HAL_DATASPACE_HEIF)) && sizesCount == 0) ||
(output && (dataspace != HAL_DATASPACE_DEPTH &&
- dataspace != HAL_DATASPACE_DYNAMIC_DEPTH) &&
+ dataspace != HAL_DATASPACE_DYNAMIC_DEPTH &&
+ dataspace != HAL_DATASPACE_HEIF) &&
mAllOutputFormats.get(format) == 0)) {
// Only throw if this is really not supported at all
throw new IllegalArgumentException("format not available");
@@ -1413,10 +1515,12 @@ public final class StreamConfigurationMap {
StreamConfiguration[] configurations =
(dataspace == HAL_DATASPACE_DEPTH) ? mDepthConfigurations :
(dataspace == HAL_DATASPACE_DYNAMIC_DEPTH) ? mDynamicDepthConfigurations :
+ (dataspace == HAL_DATASPACE_HEIF) ? mHeicConfigurations :
mConfigurations;
StreamConfigurationDuration[] minFrameDurations =
(dataspace == HAL_DATASPACE_DEPTH) ? mDepthMinFrameDurations :
(dataspace == HAL_DATASPACE_DYNAMIC_DEPTH) ? mDynamicDepthMinFrameDurations :
+ (dataspace == HAL_DATASPACE_HEIF) ? mHeicMinFrameDurations :
mMinFrameDurations;
for (StreamConfiguration config : configurations) {
@@ -1445,7 +1549,8 @@ public final class StreamConfigurationMap {
}
// Dynamic depth streams can have both fast and also high res modes.
- if ((sizeIndex != sizesCount) && (dataspace == HAL_DATASPACE_DYNAMIC_DEPTH)) {
+ if ((sizeIndex != sizesCount) && (dataspace == HAL_DATASPACE_DYNAMIC_DEPTH ||
+ dataspace == HAL_DATASPACE_HEIF)) {
if (sizeIndex > sizesCount) {
throw new AssertionError(
@@ -1485,6 +1590,9 @@ public final class StreamConfigurationMap {
// Only one publicly dynamic depth format is available.
formats[i++] = ImageFormat.DEPTH_JPEG;
}
+ if (mHeicOutputFormats.size() > 0) {
+ formats[i++] = ImageFormat.HEIC;
+ }
}
if (formats.length != i) {
throw new AssertionError("Too few formats " + i + ", expected " + formats.length);
@@ -1529,10 +1637,14 @@ public final class StreamConfigurationMap {
case DURATION_MIN_FRAME:
return (dataspace == HAL_DATASPACE_DEPTH) ? mDepthMinFrameDurations :
(dataspace == HAL_DATASPACE_DYNAMIC_DEPTH) ?
- mDynamicDepthMinFrameDurations : mMinFrameDurations;
+ mDynamicDepthMinFrameDurations :
+ (dataspace == HAL_DATASPACE_HEIF) ? mHeicMinFrameDurations :
+ mMinFrameDurations;
+
case DURATION_STALL:
return (dataspace == HAL_DATASPACE_DEPTH) ? mDepthStallDurations :
(dataspace == HAL_DATASPACE_DYNAMIC_DEPTH) ? mDynamicDepthStallDurations :
+ (dataspace == HAL_DATASPACE_HEIF) ? mHeicStallDurations :
mStallDurations;
default:
throw new IllegalArgumentException("duration was invalid");
@@ -1546,6 +1658,7 @@ public final class StreamConfigurationMap {
if (output) {
size += mDepthOutputFormats.size();
size += mDynamicDepthOutputFormats.size();
+ size += mHeicOutputFormats.size();
}
return size;
@@ -1569,6 +1682,7 @@ public final class StreamConfigurationMap {
StreamConfiguration[] configurations =
(dataspace == HAL_DATASPACE_DEPTH) ? mDepthConfigurations :
(dataspace == HAL_DATASPACE_DYNAMIC_DEPTH) ? mDynamicDepthConfigurations :
+ (dataspace == HAL_DATASPACE_HEIF) ? mHeicConfigurations :
mConfigurations;
for (int i = 0; i < configurations.length; i++) {
@@ -1767,6 +1881,8 @@ public final class StreamConfigurationMap {
return "RAW_DEPTH";
case ImageFormat.PRIVATE:
return "PRIVATE";
+ case ImageFormat.HEIC:
+ return "HEIC";
default:
return "UNKNOWN";
}
@@ -1795,7 +1911,7 @@ public final class StreamConfigurationMap {
private static final int HAL_DATASPACE_DEPTH = 0x1000;
private static final int HAL_DATASPACE_DYNAMIC_DEPTH = 0x1002;
-
+ private static final int HAL_DATASPACE_HEIF = 0x1003;
private static final long DURATION_20FPS_NS = 50000000L;
/**
* @see #getDurations(int, int)
@@ -1815,6 +1931,10 @@ public final class StreamConfigurationMap {
private final StreamConfigurationDuration[] mDynamicDepthMinFrameDurations;
private final StreamConfigurationDuration[] mDynamicDepthStallDurations;
+ private final StreamConfiguration[] mHeicConfigurations;
+ private final StreamConfigurationDuration[] mHeicMinFrameDurations;
+ private final StreamConfigurationDuration[] mHeicStallDurations;
+
private final HighSpeedVideoConfiguration[] mHighSpeedVideoConfigurations;
private final ReprocessFormatsMap mInputOutputFormatsMap;
@@ -1834,6 +1954,9 @@ public final class StreamConfigurationMap {
private final SparseIntArray mDepthOutputFormats = new SparseIntArray();
/** internal format -> num dynamic depth output sizes mapping, for HAL_DATASPACE_DYNAMIC_DEPTH */
private final SparseIntArray mDynamicDepthOutputFormats = new SparseIntArray();
+ /** internal format -> num heic output sizes mapping, for HAL_DATASPACE_HEIF */
+ private final SparseIntArray mHeicOutputFormats = new SparseIntArray();
+
/** High speed video Size -> FPS range count mapping*/
private final HashMap</*HighSpeedVideoSize*/Size, /*Count*/Integer> mHighSpeedVideoSizeMap =
new HashMap<Size, Integer>();
diff --git a/core/java/android/hardware/display/NightDisplayListener.java b/core/java/android/hardware/display/NightDisplayListener.java
new file mode 100644
index 000000000000..468f8332dc2b
--- /dev/null
+++ b/core/java/android/hardware/display/NightDisplayListener.java
@@ -0,0 +1,153 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.hardware.display;
+
+import android.annotation.NonNull;
+import android.annotation.UserIdInt;
+import android.app.ActivityManager;
+import android.content.ContentResolver;
+import android.content.Context;
+import android.database.ContentObserver;
+import android.net.Uri;
+import android.os.Handler;
+import android.os.Looper;
+import android.provider.Settings.Secure;
+
+import java.time.LocalTime;
+
+/**
+ * @hide
+ */
+public class NightDisplayListener {
+
+ private final Context mContext;
+ private final int mUserId;
+ private final ColorDisplayManager mManager;
+
+ private ContentObserver mContentObserver;
+ private Callback mCallback;
+
+ public NightDisplayListener(@NonNull Context context) {
+ this(context, ActivityManager.getCurrentUser());
+ }
+
+ public NightDisplayListener(@NonNull Context context, @UserIdInt int userId) {
+ mContext = context.getApplicationContext();
+ mUserId = userId;
+ mManager = mContext.getSystemService(ColorDisplayManager.class);
+ }
+
+ /**
+ * Register a callback to be invoked whenever the Night display settings are changed.
+ */
+ public void setCallback(Callback callback) {
+ final Callback oldCallback = mCallback;
+ if (oldCallback != callback) {
+ mCallback = callback;
+
+ if (mContentObserver == null) {
+ mContentObserver = new ContentObserver(new Handler(Looper.getMainLooper())) {
+ @Override
+ public void onChange(boolean selfChange, Uri uri) {
+ super.onChange(selfChange, uri);
+ onSettingChanged(uri);
+ }
+ };
+ }
+
+ if (callback == null) {
+ // Stop listening for changes now that there IS NOT a callback.
+ mContext.getContentResolver().unregisterContentObserver(mContentObserver);
+ } else if (oldCallback == null) {
+ // Start listening for changes now that there IS a callback.
+ final ContentResolver cr = mContext.getContentResolver();
+ cr.registerContentObserver(Secure.getUriFor(Secure.NIGHT_DISPLAY_ACTIVATED),
+ false /* notifyForDescendants */, mContentObserver, mUserId);
+ cr.registerContentObserver(Secure.getUriFor(Secure.NIGHT_DISPLAY_AUTO_MODE),
+ false /* notifyForDescendants */, mContentObserver, mUserId);
+ cr.registerContentObserver(Secure.getUriFor(Secure.NIGHT_DISPLAY_CUSTOM_START_TIME),
+ false /* notifyForDescendants */, mContentObserver, mUserId);
+ cr.registerContentObserver(Secure.getUriFor(Secure.NIGHT_DISPLAY_CUSTOM_END_TIME),
+ false /* notifyForDescendants */, mContentObserver, mUserId);
+ cr.registerContentObserver(Secure.getUriFor(Secure.NIGHT_DISPLAY_COLOR_TEMPERATURE),
+ false /* notifyForDescendants */, mContentObserver, mUserId);
+ }
+ }
+ }
+
+ private void onSettingChanged(Uri uri) {
+ final String setting = uri == null ? null : uri.getLastPathSegment();
+ if (setting == null || mCallback == null) {
+ return;
+ }
+
+ switch (setting) {
+ case Secure.NIGHT_DISPLAY_ACTIVATED:
+ mCallback.onActivated(mManager.isNightDisplayActivated());
+ break;
+ case Secure.NIGHT_DISPLAY_AUTO_MODE:
+ mCallback.onAutoModeChanged(mManager.getNightDisplayAutoMode());
+ break;
+ case Secure.NIGHT_DISPLAY_CUSTOM_START_TIME:
+ mCallback.onCustomStartTimeChanged(mManager.getNightDisplayCustomStartTime());
+ break;
+ case Secure.NIGHT_DISPLAY_CUSTOM_END_TIME:
+ mCallback.onCustomEndTimeChanged(mManager.getNightDisplayCustomEndTime());
+ break;
+ case Secure.NIGHT_DISPLAY_COLOR_TEMPERATURE:
+ mCallback.onColorTemperatureChanged(mManager.getNightDisplayColorTemperature());
+ break;
+ }
+ }
+
+ /**
+ * Callback invoked whenever the Night display settings are changed.
+ */
+ public interface Callback {
+ /**
+ * Callback invoked when the activated state changes.
+ *
+ * @param activated {@code true} if Night display is activated
+ */
+ default void onActivated(boolean activated) {}
+ /**
+ * Callback invoked when the auto mode changes.
+ *
+ * @param autoMode the auto mode to use
+ */
+ default void onAutoModeChanged(int autoMode) {}
+ /**
+ * Callback invoked when the time to automatically activate Night display changes.
+ *
+ * @param startTime the local time to automatically activate Night display
+ */
+ default void onCustomStartTimeChanged(LocalTime startTime) {}
+ /**
+ * Callback invoked when the time to automatically deactivate Night display changes.
+ *
+ * @param endTime the local time to automatically deactivate Night display
+ */
+ default void onCustomEndTimeChanged(LocalTime endTime) {}
+
+ /**
+ * Callback invoked when the color temperature changes.
+ *
+ * @param colorTemperature the color temperature to tint the screen
+ */
+ default void onColorTemperatureChanged(int colorTemperature) {}
+ }
+}
diff --git a/core/java/android/net/ConnectivityManager.java b/core/java/android/net/ConnectivityManager.java
index 8a141e2bfe6f..2aca55aacf7a 100644
--- a/core/java/android/net/ConnectivityManager.java
+++ b/core/java/android/net/ConnectivityManager.java
@@ -3923,6 +3923,25 @@ public class ConnectivityManager {
}
/**
+ * Requests that the system open the captive portal app with the specified extras.
+ *
+ * <p>This endpoint is exclusively for use by the NetworkStack and is protected by the
+ * corresponding permission.
+ * @param appExtras Extras to include in the app start intent.
+ * @hide
+ */
+ @SystemApi
+ @TestApi
+ @RequiresPermission(NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK)
+ public void startCaptivePortalApp(Bundle appExtras) {
+ try {
+ mService.startCaptivePortalAppInternal(appExtras);
+ } catch (RemoteException e) {
+ throw e.rethrowFromSystemServer();
+ }
+ }
+
+ /**
* Determine whether the device is configured to avoid bad wifi.
* @hide
*/
diff --git a/core/java/android/net/IConnectivityManager.aidl b/core/java/android/net/IConnectivityManager.aidl
index 3a405d35e9aa..872671fa5697 100644
--- a/core/java/android/net/IConnectivityManager.aidl
+++ b/core/java/android/net/IConnectivityManager.aidl
@@ -27,6 +27,7 @@ import android.net.NetworkQuotaInfo;
import android.net.NetworkRequest;
import android.net.NetworkState;
import android.net.ProxyInfo;
+import android.os.Bundle;
import android.os.IBinder;
import android.os.Messenger;
import android.os.ParcelFileDescriptor;
@@ -167,6 +168,7 @@ interface IConnectivityManager
void setAcceptUnvalidated(in Network network, boolean accept, boolean always);
void setAvoidUnvalidated(in Network network);
void startCaptivePortalApp(in Network network);
+ void startCaptivePortalAppInternal(in Bundle appExtras);
boolean getAvoidBadWifi();
int getMultipathPreference(in Network Network);
diff --git a/core/java/android/os/BatterySaverPolicyConfig.java b/core/java/android/os/BatterySaverPolicyConfig.java
index b6e2b69bbe3c..a107a7a2cfb8 100644
--- a/core/java/android/os/BatterySaverPolicyConfig.java
+++ b/core/java/android/os/BatterySaverPolicyConfig.java
@@ -47,10 +47,11 @@ public final class BatterySaverPolicyConfig implements Parcelable {
private final boolean mEnableAdjustBrightness;
private final boolean mEnableDataSaver;
private final boolean mEnableFirewall;
+ private final boolean mEnableNightMode;
private final boolean mEnableQuickDoze;
private final boolean mForceAllAppsStandby;
private final boolean mForceBackgroundCheck;
- private final int mGpsMode;
+ private final int mLocationMode;
private BatterySaverPolicyConfig(Builder in) {
mAdjustBrightnessFactor = Math.max(0, Math.min(in.mAdjustBrightnessFactor, 1f));
@@ -67,11 +68,12 @@ public final class BatterySaverPolicyConfig implements Parcelable {
mEnableAdjustBrightness = in.mEnableAdjustBrightness;
mEnableDataSaver = in.mEnableDataSaver;
mEnableFirewall = in.mEnableFirewall;
+ mEnableNightMode = in.mEnableNightMode;
mEnableQuickDoze = in.mEnableQuickDoze;
mForceAllAppsStandby = in.mForceAllAppsStandby;
mForceBackgroundCheck = in.mForceBackgroundCheck;
- mGpsMode = Math.max(PowerManager.MIN_LOCATION_MODE,
- Math.min(in.mGpsMode, PowerManager.MAX_LOCATION_MODE));
+ mLocationMode = Math.max(PowerManager.MIN_LOCATION_MODE,
+ Math.min(in.mLocationMode, PowerManager.MAX_LOCATION_MODE));
}
private BatterySaverPolicyConfig(Parcel in) {
@@ -101,10 +103,11 @@ public final class BatterySaverPolicyConfig implements Parcelable {
mEnableAdjustBrightness = in.readBoolean();
mEnableDataSaver = in.readBoolean();
mEnableFirewall = in.readBoolean();
+ mEnableNightMode = in.readBoolean();
mEnableQuickDoze = in.readBoolean();
mForceAllAppsStandby = in.readBoolean();
mForceBackgroundCheck = in.readBoolean();
- mGpsMode = Math.max(PowerManager.MIN_LOCATION_MODE,
+ mLocationMode = Math.max(PowerManager.MIN_LOCATION_MODE,
Math.min(in.readInt(), PowerManager.MAX_LOCATION_MODE));
}
@@ -150,10 +153,11 @@ public final class BatterySaverPolicyConfig implements Parcelable {
dest.writeBoolean(mEnableAdjustBrightness);
dest.writeBoolean(mEnableDataSaver);
dest.writeBoolean(mEnableFirewall);
+ dest.writeBoolean(mEnableNightMode);
dest.writeBoolean(mEnableQuickDoze);
dest.writeBoolean(mForceAllAppsStandby);
dest.writeBoolean(mForceBackgroundCheck);
- dest.writeInt(mGpsMode);
+ dest.writeInt(mLocationMode);
}
@Override
@@ -168,11 +172,12 @@ public final class BatterySaverPolicyConfig implements Parcelable {
+ "animation_disabled=" + mDisableAnimation + ","
+ "aod_disabled=" + mDisableAod + ","
+ "datasaver_disabled=" + !mEnableDataSaver + ","
+ + "enable_night_mode=" + mEnableNightMode + ","
+ "firewall_disabled=" + !mEnableFirewall + ","
+ "force_all_apps_standby=" + mForceAllAppsStandby + ","
+ "force_background_check=" + mForceBackgroundCheck + ","
+ "fullbackup_deferred=" + mDeferFullBackup + ","
- + "gps_mode=" + mGpsMode + ","
+ + "gps_mode=" + mLocationMode + ","
+ "keyvaluebackup_deferred=" + mDeferKeyValueBackup + ","
+ "launch_boost_disabled=" + mDisableLaunchBoost + ","
+ "optional_sensors_disabled=" + mDisableOptionalSensors + ","
@@ -260,6 +265,11 @@ public final class BatterySaverPolicyConfig implements Parcelable {
return mEnableFirewall;
}
+ /** Whether or not to enable night mode while in Battery Saver. */
+ public boolean getEnableNightMode() {
+ return mEnableNightMode;
+ }
+
/** Whether or not to enable Quick Doze while in Battery Saver. */
public boolean getEnableQuickDoze() {
return mEnableQuickDoze;
@@ -275,9 +285,9 @@ public final class BatterySaverPolicyConfig implements Parcelable {
return mForceBackgroundCheck;
}
- /** The GPS mode while in Battery Saver. */
- public int getGpsMode() {
- return mGpsMode;
+ /** The location mode while in Battery Saver. */
+ public int getLocationMode() {
+ return mLocationMode;
}
/** Builder class for constructing {@link BatterySaverPolicyConfig} objects. */
@@ -297,10 +307,11 @@ public final class BatterySaverPolicyConfig implements Parcelable {
private boolean mEnableAdjustBrightness = false;
private boolean mEnableDataSaver = false;
private boolean mEnableFirewall = false;
+ private boolean mEnableNightMode = false;
private boolean mEnableQuickDoze = false;
private boolean mForceAllAppsStandby = false;
private boolean mForceBackgroundCheck = false;
- private int mGpsMode = PowerManager.LOCATION_MODE_NO_CHANGE;
+ private int mLocationMode = PowerManager.LOCATION_MODE_NO_CHANGE;
public Builder() {
}
@@ -424,6 +435,13 @@ public final class BatterySaverPolicyConfig implements Parcelable {
return this;
}
+ /** Set whether or not to enable night mode while in Battery Saver. */
+ @NonNull
+ public Builder setEnableNightMode(boolean enableNightMode) {
+ mEnableNightMode = enableNightMode;
+ return this;
+ }
+
/** Set whether or not to enable Quick Doze while in Battery Saver. */
@NonNull
public Builder setEnableQuickDoze(boolean enableQuickDoze) {
@@ -445,10 +463,10 @@ public final class BatterySaverPolicyConfig implements Parcelable {
return this;
}
- /** Set the GPS mode while in Battery Saver. */
+ /** Set the location mode while in Battery Saver. */
@NonNull
- public Builder setGpsMode(@PowerManager.LocationPowerSaveMode int gpsMode) {
- mGpsMode = gpsMode;
+ public Builder setLocationMode(@PowerManager.LocationPowerSaveMode int locationMode) {
+ mLocationMode = locationMode;
return this;
}
diff --git a/core/java/android/os/IPowerManager.aidl b/core/java/android/os/IPowerManager.aidl
index 093897a3e476..bdef57518ac9 100644
--- a/core/java/android/os/IPowerManager.aidl
+++ b/core/java/android/os/IPowerManager.aidl
@@ -42,7 +42,7 @@ interface IPowerManager
boolean isWakeLockLevelSupported(int level);
void userActivity(long time, int event, int flags);
- void wakeUp(long time, String reason, String opPackageName);
+ void wakeUp(long time, int reason, String details, String opPackageName);
void goToSleep(long time, int reason, int flags);
void nap(long time);
boolean isInteractive();
diff --git a/core/java/android/os/PowerManager.java b/core/java/android/os/PowerManager.java
index be673ad14848..2ecf9d1159f0 100644
--- a/core/java/android/os/PowerManager.java
+++ b/core/java/android/os/PowerManager.java
@@ -435,6 +435,106 @@ public final class PowerManager {
public static final int GO_TO_SLEEP_FLAG_NO_DOZE = 1 << 0;
/**
+ * @hide
+ */
+ @IntDef(prefix = { "WAKE_REASON_" }, value = {
+ WAKE_REASON_UNKNOWN,
+ WAKE_REASON_POWER_BUTTON,
+ WAKE_REASON_APPLICATION,
+ WAKE_REASON_PLUGGED_IN,
+ WAKE_REASON_GESTURE,
+ WAKE_REASON_CAMERA_LAUNCH,
+ WAKE_REASON_WAKE_KEY,
+ WAKE_REASON_WAKE_MOTION,
+ WAKE_REASON_HDMI,
+ })
+ @Retention(RetentionPolicy.SOURCE)
+ public @interface WakeReason{}
+
+ /**
+ * Wake up reason code: Waking for an unknown reason.
+ * @hide
+ */
+ public static final int WAKE_REASON_UNKNOWN = 0;
+
+ /**
+ * Wake up reason code: Waking up due to power button press.
+ * @hide
+ */
+ public static final int WAKE_REASON_POWER_BUTTON = 1;
+
+ /**
+ * Wake up reason code: Waking up because an application requested it.
+ * @hide
+ */
+ public static final int WAKE_REASON_APPLICATION = 2;
+
+ /**
+ * Wake up reason code: Waking up due to being plugged in or docked on a wireless charger.
+ * @hide
+ */
+ public static final int WAKE_REASON_PLUGGED_IN = 3;
+
+ /**
+ * Wake up reason code: Waking up due to a user performed gesture (e.g. douple tapping on the
+ * screen).
+ * @hide
+ */
+ public static final int WAKE_REASON_GESTURE = 4;
+
+ /**
+ * Wake up reason code: Waking up due to the camera being launched.
+ * @hide
+ */
+ public static final int WAKE_REASON_CAMERA_LAUNCH = 5;
+
+ /**
+ * Wake up reason code: Waking up because a wake key other than power was pressed.
+ * @hide
+ */
+ public static final int WAKE_REASON_WAKE_KEY = 6;
+
+ /**
+ * Wake up reason code: Waking up because a wake motion was performed.
+ *
+ * For example, a trackball that was set to wake the device up was spun.
+ * @hide
+ */
+ public static final int WAKE_REASON_WAKE_MOTION = 7;
+
+ /**
+ * Wake up reason code: Waking due to HDMI.
+ * @hide
+ */
+ public static final int WAKE_REASON_HDMI = 8;
+
+ /**
+ * Wake up reason code: Waking due to the lid being opened.
+ * @hide
+ */
+ public static final int WAKE_REASON_LID = 9;
+
+ /**
+ * Convert the wake reason to a string for debugging purposes.
+ * @hide
+ */
+ public static String wakeReasonToString(@WakeReason int wakeReason) {
+ switch (wakeReason) {
+ case WAKE_REASON_UNKNOWN: return "WAKE_REASON_UNKNOWN";
+ case WAKE_REASON_POWER_BUTTON: return "WAKE_REASON_POWER_BUTTON";
+ case WAKE_REASON_APPLICATION: return "WAKE_REASON_APPLICATION";
+ case WAKE_REASON_PLUGGED_IN: return "WAKE_REASON_PLUGGED_IN";
+ case WAKE_REASON_GESTURE: return "WAKE_REASON_GESTURE";
+ case WAKE_REASON_CAMERA_LAUNCH: return "WAKE_REASON_CAMERA_LAUNCH";
+ case WAKE_REASON_WAKE_KEY: return "WAKE_REASON_WAKE_KEY";
+ case WAKE_REASON_WAKE_MOTION: return "WAKE_REASON_WAKE_MOTION";
+ case WAKE_REASON_HDMI: return "WAKE_REASON_HDMI";
+ case WAKE_REASON_LID: return "WAKE_REASON_LID";
+ default: return Integer.toString(wakeReason);
+ }
+ }
+
+ /**
* The value to pass as the 'reason' argument to reboot() to reboot into
* recovery mode for tasks other than applying system updates, such as
* doing factory resets.
@@ -975,22 +1075,68 @@ public final class PowerManager {
* @see #userActivity
* @see #goToSleep
*
+ * @deprecated Use {@link #wakeUp(long, int, String)} instead.
* @removed Requires signature permission.
*/
+ @Deprecated
public void wakeUp(long time) {
- try {
- mService.wakeUp(time, "wakeUp", mContext.getOpPackageName());
- } catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
- }
+ wakeUp(time, WAKE_REASON_UNKNOWN, "wakeUp");
}
/**
+ * Forces the device to wake up from sleep.
+ * <p>
+ * If the device is currently asleep, wakes it up, otherwise does nothing.
+ * This is what happens when the power key is pressed to turn on the screen.
+ * </p><p>
+ * Requires the {@link android.Manifest.permission#DEVICE_POWER} permission.
+ * </p>
+ *
+ * @param time The time when the request to wake up was issued, in the
+ * {@link SystemClock#uptimeMillis()} time base. This timestamp is used to correctly
+ * order the wake up request with other power management functions. It should be set
+ * to the timestamp of the input event that caused the request to wake up.
+ *
+ * @param details A free form string to explain the specific details behind the wake up for
+ * debugging purposes.
+ *
+ * @see #userActivity
+ * @see #goToSleep
+ *
+ * @deprecated Use {@link #wakeUp(long, int, String)} instead.
+ * @hide
+ */
+ @Deprecated
+ public void wakeUp(long time, String details) {
+ wakeUp(time, WAKE_REASON_UNKNOWN, details);
+ }
+
+ /**
+ * Forces the device to wake up from sleep.
+ * <p>
+ * If the device is currently asleep, wakes it up, otherwise does nothing.
+ * This is what happens when the power key is pressed to turn on the screen.
+ * </p><p>
+ * Requires the {@link android.Manifest.permission#DEVICE_POWER} permission.
+ * </p>
+ *
+ * @param time The time when the request to wake up was issued, in the
+ * {@link SystemClock#uptimeMillis()} time base. This timestamp is used to correctly
+ * order the wake up request with other power management functions. It should be set
+ * to the timestamp of the input event that caused the request to wake up.
+ *
+ * @param reason The reason for the wake up.
+ *
+ * @param details A free form string to explain the specific details behind the wake up for
+ * debugging purposes.
+ *
+ * @see #userActivity
+ * @see #goToSleep
* @hide
*/
- public void wakeUp(long time, String reason) {
+ public void wakeUp(long time, @WakeReason int reason, String details) {
try {
- mService.wakeUp(time, reason, mContext.getOpPackageName());
+ mService.wakeUp(time, reason, details, mContext.getOpPackageName());
} catch (RemoteException e) {
throw e.rethrowFromSystemServer();
}
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index a8976aa56241..e95d60465371 100644
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -9300,6 +9300,13 @@ public final class Settings {
public static final String DEBUG_VIEW_ATTRIBUTES = "debug_view_attributes";
/**
+ * Which application package is allowed to save View attribute data.
+ * @hide
+ */
+ public static final String DEBUG_VIEW_ATTRIBUTES_APPLICATION_PACKAGE =
+ "debug_view_attributes_application_package";
+
+ /**
* Whether assisted GPS should be enabled or not.
* @hide
*/
@@ -14022,6 +14029,7 @@ public final class Settings {
INSTANT_APP_SETTINGS.add(TRANSITION_ANIMATION_SCALE);
INSTANT_APP_SETTINGS.add(ANIMATOR_DURATION_SCALE);
INSTANT_APP_SETTINGS.add(DEBUG_VIEW_ATTRIBUTES);
+ INSTANT_APP_SETTINGS.add(DEBUG_VIEW_ATTRIBUTES_APPLICATION_PACKAGE);
INSTANT_APP_SETTINGS.add(WTF_IS_FATAL);
INSTANT_APP_SETTINGS.add(SEND_ACTION_APP_ERROR);
INSTANT_APP_SETTINGS.add(ZEN_MODE);
diff --git a/core/java/android/service/dreams/Sandman.java b/core/java/android/service/dreams/Sandman.java
index eeb340b67e68..efb8923a459f 100644
--- a/core/java/android/service/dreams/Sandman.java
+++ b/core/java/android/service/dreams/Sandman.java
@@ -91,8 +91,9 @@ public final class Sandman {
// and the UI mode manager starting a dream. We want the system to already
// be awake by the time this happens. Otherwise the dream may not start.
PowerManager powerManager =
- (PowerManager)context.getSystemService(Context.POWER_SERVICE);
+ context.getSystemService(PowerManager.class);
powerManager.wakeUp(SystemClock.uptimeMillis(),
+ PowerManager.WAKE_REASON_PLUGGED_IN,
"android.service.dreams:DREAM");
} else {
Slog.i(TAG, "Activating dream by user request.");
diff --git a/core/java/android/text/TextLine.java b/core/java/android/text/TextLine.java
index 949328fd3a99..915a18e59226 100644
--- a/core/java/android/text/TextLine.java
+++ b/core/java/android/text/TextLine.java
@@ -94,7 +94,8 @@ public class TextLine {
private final DecorationInfo mDecorationInfo = new DecorationInfo();
private final ArrayList<DecorationInfo> mDecorations = new ArrayList<>();
- @UnsupportedAppUsage
+ /** Not allowed to access. If it's for memory leak workaround, it was already fixed M. */
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
private static final TextLine[] sCached = new TextLine[3];
/**
diff --git a/core/java/android/view/AccessibilityInteractionController.java b/core/java/android/view/AccessibilityInteractionController.java
index 59e562fe8071..62ed901c5e06 100644
--- a/core/java/android/view/AccessibilityInteractionController.java
+++ b/core/java/android/view/AccessibilityInteractionController.java
@@ -40,6 +40,7 @@ import android.util.Slog;
import android.view.View.AttachInfo;
import android.view.accessibility.AccessibilityInteractionClient;
import android.view.accessibility.AccessibilityManager;
+import android.view.accessibility.AccessibilityNodeIdManager;
import android.view.accessibility.AccessibilityNodeInfo;
import android.view.accessibility.AccessibilityNodeInfo.AccessibilityAction;
import android.view.accessibility.AccessibilityNodeProvider;
@@ -154,13 +155,7 @@ public final class AccessibilityInteractionController {
}
private boolean isShown(View view) {
- // The first two checks are made also made by isShown() which
- // however traverses the tree up to the parent to catch that.
- // Therefore, we do some fail fast check to minimize the up
- // tree traversal.
- return (view.mAttachInfo != null
- && view.mAttachInfo.mWindowVisibility == View.VISIBLE
- && view.isShown());
+ return (view != null) && (view.getWindowVisibility() == View.VISIBLE && view.isShown());
}
public void findAccessibilityNodeInfoByAccessibilityIdClientThread(
@@ -340,13 +335,8 @@ public final class AccessibilityInteractionController {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
- View root = null;
- if (accessibilityViewId == AccessibilityNodeInfo.ROOT_ITEM_ID) {
- root = mViewRootImpl.mView;
- } else {
- root = findViewByAccessibilityId(accessibilityViewId);
- }
- if (root != null && isShown(root)) {
+ final View root = findViewByAccessibilityId(accessibilityViewId);
+ if (root != null) {
mPrefetcher.prefetchAccessibilityNodeInfos(
root, virtualDescendantId, flags, infos, arguments);
}
@@ -396,12 +386,7 @@ public final class AccessibilityInteractionController {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
- View root = null;
- if (accessibilityViewId != AccessibilityNodeInfo.ROOT_ITEM_ID) {
- root = findViewByAccessibilityId(accessibilityViewId);
- } else {
- root = mViewRootImpl.mView;
- }
+ final View root = findViewByAccessibilityId(accessibilityViewId);
if (root != null) {
final int resolvedViewId = root.getContext().getResources()
.getIdentifier(viewId, null, null);
@@ -462,13 +447,8 @@ public final class AccessibilityInteractionController {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
- View root = null;
- if (accessibilityViewId != AccessibilityNodeInfo.ROOT_ITEM_ID) {
- root = findViewByAccessibilityId(accessibilityViewId);
- } else {
- root = mViewRootImpl.mView;
- }
- if (root != null && isShown(root)) {
+ final View root = findViewByAccessibilityId(accessibilityViewId);
+ if (root != null) {
AccessibilityNodeProvider provider = root.getAccessibilityNodeProvider();
if (provider != null) {
infos = provider.findAccessibilityNodeInfosByText(text,
@@ -550,13 +530,8 @@ public final class AccessibilityInteractionController {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
- View root = null;
- if (accessibilityViewId != AccessibilityNodeInfo.ROOT_ITEM_ID) {
- root = findViewByAccessibilityId(accessibilityViewId);
- } else {
- root = mViewRootImpl.mView;
- }
- if (root != null && isShown(root)) {
+ final View root = findViewByAccessibilityId(accessibilityViewId);
+ if (root != null) {
switch (focusType) {
case AccessibilityNodeInfo.FOCUS_ACCESSIBILITY: {
View host = mViewRootImpl.mAccessibilityFocusedHost;
@@ -583,7 +558,7 @@ public final class AccessibilityInteractionController {
} break;
case AccessibilityNodeInfo.FOCUS_INPUT: {
View target = root.findFocus();
- if (target == null || !isShown(target)) {
+ if (!isShown(target)) {
break;
}
AccessibilityNodeProvider provider = target.getAccessibilityNodeProvider();
@@ -645,13 +620,8 @@ public final class AccessibilityInteractionController {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
- View root = null;
- if (accessibilityViewId != AccessibilityNodeInfo.ROOT_ITEM_ID) {
- root = findViewByAccessibilityId(accessibilityViewId);
- } else {
- root = mViewRootImpl.mView;
- }
- if (root != null && isShown(root)) {
+ final View root = findViewByAccessibilityId(accessibilityViewId);
+ if (root != null) {
View nextView = root.focusSearch(direction);
if (nextView != null) {
next = nextView.createAccessibilityNodeInfo();
@@ -705,13 +675,8 @@ public final class AccessibilityInteractionController {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
- View target = null;
- if (accessibilityViewId != AccessibilityNodeInfo.ROOT_ITEM_ID) {
- target = findViewByAccessibilityId(accessibilityViewId);
- } else {
- target = mViewRootImpl.mView;
- }
- if (target != null && isShown(target)) {
+ final View target = findViewByAccessibilityId(accessibilityViewId);
+ if (target != null) {
if (action == R.id.accessibilityActionClickOnClickableSpan) {
// Handle this hidden action separately
succeeded = handleClickableSpanActionUiThread(
@@ -791,15 +756,13 @@ public final class AccessibilityInteractionController {
}
private View findViewByAccessibilityId(int accessibilityId) {
- View root = mViewRootImpl.mView;
- if (root == null) {
- return null;
- }
- View foundView = root.findViewByAccessibilityId(accessibilityId);
- if (foundView != null && !isShown(foundView)) {
- return null;
+ if (accessibilityId == AccessibilityNodeInfo.ROOT_ITEM_ID) {
+ return mViewRootImpl.mView;
+ } else {
+ final View foundView =
+ AccessibilityNodeIdManager.getInstance().findView(accessibilityId);
+ return isShown(foundView) ? foundView : null;
}
- return foundView;
}
private void applyAppScaleAndMagnificationSpecIfNeeded(List<AccessibilityNodeInfo> infos,
@@ -1171,7 +1134,7 @@ public final class AccessibilityInteractionController {
}
View child = children.get(i);
if (child.getAccessibilityViewId() != current.getAccessibilityViewId()
- && isShown(child)) {
+ && isShown(child)) {
AccessibilityNodeInfo info = null;
AccessibilityNodeProvider provider =
child.getAccessibilityNodeProvider();
diff --git a/core/java/android/view/RemotableViewMethod.java b/core/java/android/view/RemotableViewMethod.java
index 03aed9a53925..5eff848e85aa 100644
--- a/core/java/android/view/RemotableViewMethod.java
+++ b/core/java/android/view/RemotableViewMethod.java
@@ -16,6 +16,8 @@
package android.view;
+import android.annotation.TestApi;
+
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@@ -26,6 +28,7 @@ import java.lang.annotation.Target;
* This annotation indicates that a method on a subclass of View
* is alllowed to be used with the {@link android.widget.RemoteViews} mechanism.
*/
+@TestApi
@Target({ ElementType.METHOD })
@Retention(RetentionPolicy.RUNTIME)
public @interface RemotableViewMethod {
diff --git a/core/java/android/view/SurfaceControl.java b/core/java/android/view/SurfaceControl.java
index c0a4028c0301..8028715219cc 100644
--- a/core/java/android/view/SurfaceControl.java
+++ b/core/java/android/view/SurfaceControl.java
@@ -852,12 +852,11 @@ public final class SurfaceControl implements Parcelable {
}
/**
- * Free all server-side state associated with this surface and
- * release this object's reference. This method can only be
- * called from the process that created the service.
+ * Release the local resources like {@link #release} but also
+ * remove the Surface from the screen.
* @hide
*/
- public void destroy() {
+ public void remove() {
if (mNativeObject != 0) {
nativeDestroy(mNativeObject);
mNativeObject = 0;
@@ -2467,5 +2466,23 @@ public final class SurfaceControl implements Parcelable {
nativeMergeTransaction(mNativeObject, other.mNativeObject);
return this;
}
+
+ /**
+ * Equivalent to reparent with a null parent, in that it removes
+ * the SurfaceControl from the scene, but it also releases
+ * the local resources (by calling {@link SurfaceControl#release})
+ * after this method returns, {@link SurfaceControl#isValid} will return
+ * false for the argument.
+ *
+ * @param sc The surface to remove and release.
+ * @return This transaction
+ * @hide
+ */
+ @NonNull
+ public Transaction remove(@NonNull SurfaceControl sc) {
+ reparent(sc, null);
+ sc.release();
+ return this;
+ }
}
}
diff --git a/core/java/android/view/SurfaceView.java b/core/java/android/view/SurfaceView.java
index cd5207c50d1d..9f0800f11721 100644
--- a/core/java/android/view/SurfaceView.java
+++ b/core/java/android/view/SurfaceView.java
@@ -334,7 +334,7 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
updateSurface();
if (mSurfaceControl != null) {
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
}
mSurfaceControl = null;
@@ -502,11 +502,11 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
private void releaseSurfaces() {
if (mSurfaceControl != null) {
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
mSurfaceControl = null;
}
if (mBackgroundControl != null) {
- mBackgroundControl.destroy();
+ mBackgroundControl.remove();
mBackgroundControl = null;
}
}
@@ -816,7 +816,7 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
}
if (mDeferredDestroySurfaceControl != null) {
- mDeferredDestroySurfaceControl.destroy();
+ mDeferredDestroySurfaceControl.remove();
mDeferredDestroySurfaceControl = null;
}
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index 04ffa33d0e22..c641552d8d72 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -35,6 +35,7 @@ import android.annotation.LayoutRes;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.Size;
+import android.annotation.StyleRes;
import android.annotation.TestApi;
import android.annotation.UiThread;
import android.annotation.UnsupportedAppUsage;
@@ -91,6 +92,7 @@ import android.util.LongSparseLongArray;
import android.util.Pools.SynchronizedPool;
import android.util.Property;
import android.util.SparseArray;
+import android.util.SparseIntArray;
import android.util.StateSet;
import android.util.SuperNotCalledException;
import android.util.TypedValue;
@@ -103,6 +105,7 @@ import android.view.WindowInsetsAnimationListener.InsetsAnimation;
import android.view.accessibility.AccessibilityEvent;
import android.view.accessibility.AccessibilityEventSource;
import android.view.accessibility.AccessibilityManager;
+import android.view.accessibility.AccessibilityNodeIdManager;
import android.view.accessibility.AccessibilityNodeInfo;
import android.view.accessibility.AccessibilityNodeInfo.AccessibilityAction;
import android.view.accessibility.AccessibilityNodeProvider;
@@ -820,7 +823,14 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
*
* @hide
*/
- public static boolean mDebugViewAttributes = false;
+ public static boolean sDebugViewAttributes = false;
+
+ /**
+ * When set to this application package view will save its attribute data.
+ *
+ * @hide
+ */
+ public static String sDebugViewAttributesApplicationPackage;
/**
* Used to mark a View that has no ID.
@@ -5078,6 +5088,15 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
@LayoutRes
private int mSourceLayoutId = ID_NULL;
+ @Nullable
+ private SparseIntArray mAttributeSourceResId;
+
+ @Nullable
+ private int[] mAttributeResolutionStack;
+
+ @StyleRes
+ private int mExplicitStyle;
+
/**
* Cached reference to the {@link ContentCaptureSession}, is reset on {@link #invalidate()}.
*/
@@ -5253,7 +5272,11 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
final TypedArray a = context.obtainStyledAttributes(
attrs, com.android.internal.R.styleable.View, defStyleAttr, defStyleRes);
- if (mDebugViewAttributes) {
+ retrieveExplicitStyle(context.getTheme(), attrs);
+ saveAttributeDataForStyleable(context, com.android.internal.R.styleable.View, attrs, a,
+ defStyleAttr, defStyleRes);
+
+ if (sDebugViewAttributes) {
saveAttributeData(attrs, a);
}
@@ -5915,6 +5938,84 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
}
/**
+ * Returns the ordered list of resource ID that are considered when resolving attribute values
+ * for this {@link View}. The list will include layout resource ID if the View is inflated from
+ * XML. It will also include a set of explicit styles if specified in XML using
+ * {@code style="..."}. Finally, it will include the default styles resolved from the theme.
+ *
+ * <p>
+ * <b>Note:</b> this method will only return actual values if the view attribute debugging
+ * is enabled in Android developer options.
+ *
+ * @return ordered list of resource ID that are considered when resolving attribute values for
+ * this {@link View}.
+ */
+ @NonNull
+ public List<Integer> getAttributeResolutionStack() {
+ ArrayList<Integer> stack = new ArrayList<>();
+ if (!sDebugViewAttributes) {
+ return stack;
+ }
+ if (mSourceLayoutId != ID_NULL) {
+ stack.add(mSourceLayoutId);
+ }
+ for (int i = 0; i < mAttributeResolutionStack.length; i++) {
+ stack.add(mAttributeResolutionStack[i]);
+ }
+ return stack;
+ }
+
+ /**
+ * Returns the mapping of attribute resource ID to source resource ID where the attribute value
+ * was set. Source resource ID can either be a layout resource ID, if the value was set in XML
+ * within the View tag, or a style resource ID, if the attribute was set in a style. The source
+ * resource value will be one of the resource IDs from {@link #getAttributeSourceResourceMap()}.
+ *
+ * <p>
+ * <b>Note:</b> this method will only return actual values if the view attribute debugging
+ * is enabled in Android developer options.
+ *
+ * @return mapping of attribute resource ID to source resource ID where the attribute value
+ * was set.
+ */
+ @NonNull
+ public Map<Integer, Integer> getAttributeSourceResourceMap() {
+ HashMap<Integer, Integer> map = new HashMap<>();
+ if (!sDebugViewAttributes) {
+ return map;
+ }
+ for (int i = 0; i < mAttributeSourceResId.size(); i++) {
+ map.put(mAttributeSourceResId.keyAt(i), mAttributeSourceResId.valueAt(i));
+ }
+ return map;
+ }
+
+ /**
+ * Returns the resource ID for the style specified using {@code style="..."} in the
+ * {@link AttributeSet}'s backing XML element or {@link Resources#ID_NULL} otherwise if not
+ * specified or otherwise not applicable.
+ * <p>
+ * Each {@link View} can have an explicit style specified in the layout file.
+ * This style is used first during the {@link View} attribute resolution, then if an attribute
+ * is not defined there the resource system looks at default style and theme as fallbacks.
+ *
+ * <p>
+ * <b>Note:</b> this method will only return actual values if the view attribute debugging
+ * is enabled in Android developer options.
+ *
+ * @return The resource ID for the style specified using {@code style="..."} in the
+ * {@link AttributeSet}'s backing XML element or {@link Resources#ID_NULL} otherwise
+ * if not specified or otherwise not applicable.
+ */
+ @StyleRes
+ public int getExplicitStyle() {
+ if (!sDebugViewAttributes) {
+ return ID_NULL;
+ }
+ return mExplicitStyle;
+ }
+
+ /**
* An implementation of OnClickListener that attempts to lazily load a
* named click handling method from a parent or ancestor context.
*/
@@ -6000,6 +6101,46 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
return mAttributeMap;
}
+ private void retrieveExplicitStyle(@NonNull Resources.Theme theme,
+ @Nullable AttributeSet attrs) {
+ if (!sDebugViewAttributes) {
+ return;
+ }
+ mExplicitStyle = theme.getExplicitStyle(attrs);
+ }
+
+ /**
+ * Stores debugging information about attributes. This should be called in a constructor by
+ * every custom {@link View} that uses a custom styleable.
+ * @param context Context under which this view is created.
+ * @param styleable A reference to styleable array R.styleable.Foo
+ * @param attrs AttributeSet used to construct this view.
+ * @param t Resolved {@link TypedArray} returned by a call to
+ * {@link Resources#obtainAttributes(AttributeSet, int[])}.
+ * @param defStyleAttr Default style attribute passed into the view constructor.
+ * @param defStyleRes Default style resource passed into the view constructor.
+ */
+ public final void saveAttributeDataForStyleable(@NonNull Context context,
+ @NonNull int[] styleable, @Nullable AttributeSet attrs, @NonNull TypedArray t,
+ int defStyleAttr, int defStyleRes) {
+ if (!sDebugViewAttributes) {
+ return;
+ }
+
+ mAttributeResolutionStack = context.getTheme().getAttributeResolutionStack(
+ defStyleAttr, defStyleRes, mExplicitStyle);
+
+ if (mAttributeSourceResId == null) {
+ mAttributeSourceResId = new SparseIntArray();
+ }
+
+ final int indexCount = t.getIndexCount();
+ for (int j = 0; j < indexCount; ++j) {
+ final int index = t.getIndex(j);
+ mAttributeSourceResId.append(styleable[index], t.getSourceResourceId(index, 0));
+ }
+ }
+
private void saveAttributeData(@Nullable AttributeSet attrs, @NonNull TypedArray t) {
final int attrsCount = attrs == null ? 0 : attrs.getAttributeCount();
final int indexCount = t.getIndexCount();
@@ -19041,6 +19182,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
jumpDrawablesToCurrentState();
+ AccessibilityNodeIdManager.getInstance().registerViewWithId(this, getAccessibilityViewId());
resetSubtreeAccessibilityStateChanged();
// rebuild, since Outline not maintained while View is detached
@@ -19433,6 +19575,8 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
if ((mViewFlags & TOOLTIP) == TOOLTIP) {
hideTooltip();
}
+
+ AccessibilityNodeIdManager.getInstance().unregisterViewWithId(getAccessibilityViewId());
}
private void cleanupDraw() {
@@ -23947,24 +24091,6 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
}
/**
- * Finds a view by its unuque and stable accessibility id.
- *
- * @param accessibilityId The searched accessibility id.
- * @return The found view.
- */
- @UnsupportedAppUsage
- final <T extends View> T findViewByAccessibilityId(int accessibilityId) {
- if (accessibilityId < 0) {
- return null;
- }
- T view = findViewByAccessibilityIdTraversal(accessibilityId);
- if (view != null) {
- return view.includeForAccessibility() ? view : null;
- }
- return null;
- }
-
- /**
* Performs the traversal to find a view by its unique and stable accessibility id.
*
* <strong>Note:</strong>This method does not stop at the root namespace
diff --git a/core/java/android/view/ViewRootImpl.java b/core/java/android/view/ViewRootImpl.java
index 47528a05f5a2..156972f6ecbb 100644
--- a/core/java/android/view/ViewRootImpl.java
+++ b/core/java/android/view/ViewRootImpl.java
@@ -95,6 +95,7 @@ import android.view.accessibility.AccessibilityEvent;
import android.view.accessibility.AccessibilityManager;
import android.view.accessibility.AccessibilityManager.AccessibilityStateChangeListener;
import android.view.accessibility.AccessibilityManager.HighTextContrastChangeListener;
+import android.view.accessibility.AccessibilityNodeIdManager;
import android.view.accessibility.AccessibilityNodeInfo;
import android.view.accessibility.AccessibilityNodeInfo.AccessibilityAction;
import android.view.accessibility.AccessibilityNodeProvider;
@@ -1602,7 +1603,7 @@ public final class ViewRootImpl implements ViewParent,
mSurfaceSession = null;
if (mBoundsSurfaceControl != null) {
- mBoundsSurfaceControl.destroy();
+ mBoundsSurfaceControl.remove();
mBoundsSurface.release();
mBoundsSurfaceControl = null;
}
@@ -7954,17 +7955,14 @@ public final class ViewRootImpl implements ViewParent,
// Intercept accessibility focus events fired by virtual nodes to keep
// track of accessibility focus position in such nodes.
final int eventType = event.getEventType();
+ final View source = getSourceForAccessibilityEvent(event);
switch (eventType) {
case AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUSED: {
- final long sourceNodeId = event.getSourceNodeId();
- final int accessibilityViewId = AccessibilityNodeInfo.getAccessibilityViewId(
- sourceNodeId);
- View source = mView.findViewByAccessibilityId(accessibilityViewId);
if (source != null) {
AccessibilityNodeProvider provider = source.getAccessibilityNodeProvider();
if (provider != null) {
final int virtualNodeId = AccessibilityNodeInfo.getVirtualDescendantId(
- sourceNodeId);
+ event.getSourceNodeId());
final AccessibilityNodeInfo node;
node = provider.createAccessibilityNodeInfo(virtualNodeId);
setAccessibilityFocus(source, node);
@@ -7972,15 +7970,8 @@ public final class ViewRootImpl implements ViewParent,
}
} break;
case AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUS_CLEARED: {
- final long sourceNodeId = event.getSourceNodeId();
- final int accessibilityViewId = AccessibilityNodeInfo.getAccessibilityViewId(
- sourceNodeId);
- View source = mView.findViewByAccessibilityId(accessibilityViewId);
- if (source != null) {
- AccessibilityNodeProvider provider = source.getAccessibilityNodeProvider();
- if (provider != null) {
- setAccessibilityFocus(null, null);
- }
+ if (source != null && source.getAccessibilityNodeProvider() != null) {
+ setAccessibilityFocus(null, null);
}
} break;
@@ -7993,6 +7984,13 @@ public final class ViewRootImpl implements ViewParent,
return true;
}
+ private View getSourceForAccessibilityEvent(AccessibilityEvent event) {
+ final long sourceNodeId = event.getSourceNodeId();
+ final int accessibilityViewId = AccessibilityNodeInfo.getAccessibilityViewId(
+ sourceNodeId);
+ return AccessibilityNodeIdManager.getInstance().findView(accessibilityViewId);
+ }
+
/**
* Updates the focused virtual view, when necessary, in response to a
* content changed event.
diff --git a/core/java/android/view/WindowManagerPolicyConstants.java b/core/java/android/view/WindowManagerPolicyConstants.java
index 16bafe2c4f11..35ed7bfa2ce6 100644
--- a/core/java/android/view/WindowManagerPolicyConstants.java
+++ b/core/java/android/view/WindowManagerPolicyConstants.java
@@ -16,6 +16,11 @@
package android.view;
+import android.annotation.IntDef;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+
/**
* Constants for interfacing with WindowManagerService and WindowManagerPolicyInternal.
* @hide
@@ -89,6 +94,35 @@ public interface WindowManagerPolicyConstants {
/** Screen turned off because of timeout */
int OFF_BECAUSE_OF_TIMEOUT = 3;
+ @IntDef(prefix = { "ON_BECAUSE_OF_" }, value = {
+ ON_BECAUSE_OF_USER,
+ ON_BECAUSE_OF_APPLICATION,
+ ON_BECAUSE_OF_UNKNOWN,
+ })
+ @Retention(RetentionPolicy.SOURCE)
+ public @interface OnReason{}
+
+ /** Convert the on reason to a human readable format */
+ static String onReasonToString(@OnReason int why) {
+ switch (why) {
+ case ON_BECAUSE_OF_USER:
+ return "ON_BECAUSE_OF_USER";
+ case ON_BECAUSE_OF_APPLICATION:
+ return "ON_BECAUSE_OF_APPLICATION";
+ case ON_BECAUSE_OF_UNKNOWN:
+ return "ON_BECAUSE_OF_UNKNOWN";
+ default:
+ return Integer.toString(why);
+ }
+ }
+
+ /** Screen turned on because of a user-initiated action. */
+ int ON_BECAUSE_OF_USER = 1;
+ /** Screen turned on because of an application request or event */
+ int ON_BECAUSE_OF_APPLICATION = 2;
+ /** Screen turned on for an unknown reason */
+ int ON_BECAUSE_OF_UNKNOWN = 3;
+
int APPLICATION_LAYER = 2;
int APPLICATION_MEDIA_SUBLAYER = -2;
int APPLICATION_MEDIA_OVERLAY_SUBLAYER = -1;
diff --git a/core/java/android/view/accessibility/AccessibilityManager.java b/core/java/android/view/accessibility/AccessibilityManager.java
index 6aafa348e3f5..06207a9290d7 100644
--- a/core/java/android/view/accessibility/AccessibilityManager.java
+++ b/core/java/android/view/accessibility/AccessibilityManager.java
@@ -36,6 +36,7 @@ import android.content.pm.PackageManager;
import android.content.pm.ServiceInfo;
import android.content.res.Resources;
import android.os.Binder;
+import android.os.Build;
import android.os.Handler;
import android.os.IBinder;
import android.os.Looper;
@@ -183,7 +184,7 @@ public final class AccessibilityManager {
boolean mIsTouchExplorationEnabled;
- @UnsupportedAppUsage
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P, trackingBug = 123768939)
boolean mIsHighTextContrastEnabled;
AccessibilityPolicy mAccessibilityPolicy;
diff --git a/core/java/android/view/accessibility/AccessibilityNodeIdManager.java b/core/java/android/view/accessibility/AccessibilityNodeIdManager.java
new file mode 100644
index 000000000000..1ac704774e7f
--- /dev/null
+++ b/core/java/android/view/accessibility/AccessibilityNodeIdManager.java
@@ -0,0 +1,68 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.view.accessibility;
+
+import android.util.SparseArray;
+import android.view.View;
+
+/** @hide */
+public final class AccessibilityNodeIdManager {
+ private SparseArray<View> mIdsToViews = new SparseArray<>();
+ private static AccessibilityNodeIdManager sIdManager;
+
+ /**
+ * Gets singleton.
+ * @return The instance.
+ */
+ public static synchronized AccessibilityNodeIdManager getInstance() {
+ if (sIdManager == null) {
+ sIdManager = new AccessibilityNodeIdManager();
+ }
+ return sIdManager;
+ }
+
+ private AccessibilityNodeIdManager() {
+ }
+
+ /**
+ * Register view to be kept track of by the accessibility system.
+ * Must be paired with unregisterView, otherwise this will leak.
+ * @param view The view to be registered.
+ * @param id The accessibilityViewId of the view.
+ */
+ public void registerViewWithId(View view, int id) {
+ mIdsToViews.append(id, view);
+ }
+
+ /**
+ * Unregister view, accessibility won't keep track of this view after this call.
+ * @param id The id returned from registerView when the view as first associated.
+ */
+ public void unregisterViewWithId(int id) {
+ mIdsToViews.remove(id);
+ }
+
+ /**
+ * Accessibility uses this to find the view in the hierarchy.
+ * @param id The accessibility view id.
+ * @return The view.
+ */
+ public View findView(int id) {
+ final View view = mIdsToViews.get(id);
+ return view != null && view.includeForAccessibility() ? view : null;
+ }
+}
diff --git a/core/java/android/view/autofill/AutofillId.java b/core/java/android/view/autofill/AutofillId.java
index f1c7b695ce05..5608bb372701 100644
--- a/core/java/android/view/autofill/AutofillId.java
+++ b/core/java/android/view/autofill/AutofillId.java
@@ -52,11 +52,13 @@ public final class AutofillId implements Parcelable {
}
/** @hide */
+ @TestApi
public AutofillId(int parentId, int virtualChildId) {
this(FLAG_IS_VIRTUAL_INT, parentId, virtualChildId, NO_SESSION);
}
/** @hide */
+ @TestApi
public AutofillId(@NonNull AutofillId parent, long virtualChildId, int sessionId) {
this(FLAG_IS_VIRTUAL_LONG | FLAG_HAS_SESSION, parent.mViewId, virtualChildId, sessionId);
}
diff --git a/core/java/android/view/autofill/AutofillManager.java b/core/java/android/view/autofill/AutofillManager.java
index 1c96b87394b6..83fc017373a6 100644
--- a/core/java/android/view/autofill/AutofillManager.java
+++ b/core/java/android/view/autofill/AutofillManager.java
@@ -346,9 +346,6 @@ public final class AutofillManager {
@TestApi
public static final int FLAG_SMART_SUGGESTION_SYSTEM = 0x1;
- /** @hide */ // TODO(b/123233342): remove when not used anymore
- public static final int FLAG_SMART_SUGGESTION_LEGACY = 0x2;
-
/** @hide */
@IntDef(flag = true, prefix = { "FLAG_SMART_SUGGESTION_" }, value = {
FLAG_SMART_SUGGESTION_SYSTEM
diff --git a/core/java/android/view/contentcapture/ContentCaptureEvent.java b/core/java/android/view/contentcapture/ContentCaptureEvent.java
index dfac35ddf58b..22254cd94059 100644
--- a/core/java/android/view/contentcapture/ContentCaptureEvent.java
+++ b/core/java/android/view/contentcapture/ContentCaptureEvent.java
@@ -138,8 +138,11 @@ public final class ContentCaptureEvent implements Parcelable {
/**
* Adds an autofill id to the this event, merging the single id into a list if necessary.
- * @hide */
+ *
+ * @hide
+ */
public ContentCaptureEvent addAutofillId(@NonNull AutofillId id) {
+ Preconditions.checkNotNull(id);
if (mIds == null) {
mIds = new ArrayList<>();
if (mId == null) {
diff --git a/core/java/android/view/contentcapture/ViewNode.java b/core/java/android/view/contentcapture/ViewNode.java
index eef841da3bc5..8d6245458d62 100644
--- a/core/java/android/view/contentcapture/ViewNode.java
+++ b/core/java/android/view/contentcapture/ViewNode.java
@@ -34,7 +34,6 @@ import android.view.ViewStructure.HtmlInfo.Builder;
import android.view.autofill.AutofillId;
import android.view.autofill.AutofillValue;
-import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.util.Preconditions;
//TODO(b/122484602): add javadocs / implement Parcelable / implement
@@ -589,6 +588,7 @@ public final class ViewNode extends AssistStructure.ViewNode {
}
/** @hide */
+ @TestApi
public static void writeToParcel(@NonNull Parcel parcel, @Nullable ViewNode node, int flags) {
if (node == null) {
parcel.writeLong(0);
@@ -598,18 +598,20 @@ public final class ViewNode extends AssistStructure.ViewNode {
}
/** @hide */
+ @TestApi
public static @Nullable ViewNode readFromParcel(@NonNull Parcel parcel) {
final long nodeFlags = parcel.readLong();
- return nodeFlags == 0 ? new ViewNode() : new ViewNode(nodeFlags, parcel);
+ return nodeFlags == 0 ? null : new ViewNode(nodeFlags, parcel);
}
/** @hide */
- @VisibleForTesting // Must be public to be accessed from FrameworkCoreTests' apk.
+ @TestApi
public static final class ViewStructureImpl extends ViewStructure {
final ViewNode mNode = new ViewNode();
- @VisibleForTesting // Must be public to be accessed from FrameworkCoreTests' apk.
+ /** @hide */
+ @TestApi
public ViewStructureImpl(@NonNull View view) {
mNode.mAutofillId = Preconditions.checkNotNull(view).getAutofillId();
final ViewParent parent = view.getParent();
@@ -618,13 +620,15 @@ public final class ViewNode extends AssistStructure.ViewNode {
}
}
- @VisibleForTesting // Must be public to be accessed from FrameworkCoreTests' apk.
+ /** @hide */
+ @TestApi
public ViewStructureImpl(@NonNull AutofillId parentId, long virtualId, int sessionId) {
mNode.mParentAutofillId = Preconditions.checkNotNull(parentId);
mNode.mAutofillId = new AutofillId(parentId, virtualId, sessionId);
}
- @VisibleForTesting // Must be public to be accessed from FrameworkCoreTests' apk.
+ /** @hide */
+ @TestApi
public ViewNode getNode() {
return mNode;
}
diff --git a/core/java/android/view/inputmethod/InputMethodManager.java b/core/java/android/view/inputmethod/InputMethodManager.java
index aee4b1f63812..8a097883dd5c 100644
--- a/core/java/android/view/inputmethod/InputMethodManager.java
+++ b/core/java/android/view/inputmethod/InputMethodManager.java
@@ -339,7 +339,11 @@ public final class InputMethodManager {
// For scheduling work on the main thread. This also serves as our
// global lock.
- @UnsupportedAppUsage
+ // Remark on @UnsupportedAppUsage: there were context leaks on old versions
+ // of android (b/37043700), so developers used this field to perform manual clean up.
+ // Leaks were fixed, hacks were backported to AppCompatActivity,
+ // so an access to the field is closed.
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
final H mH;
// Our generic input connection if the current target does not have its own.
@@ -375,13 +379,15 @@ public final class InputMethodManager {
* This is the view that should currently be served by an input method,
* regardless of the state of setting that up.
*/
- @UnsupportedAppUsage
+ // See comment to mH field in regard to @UnsupportedAppUsage
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
View mServedView;
/**
* This is then next view that will be served by the input method, when
* we get around to updating things.
*/
- @UnsupportedAppUsage
+ // See comment to mH field in regard to @UnsupportedAppUsage
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
View mNextServedView;
/**
* This is set when we are in the process of connecting, to determine
diff --git a/core/java/android/widget/AbsListView.java b/core/java/android/widget/AbsListView.java
index cc45f38b0ea3..542df4562908 100644
--- a/core/java/android/widget/AbsListView.java
+++ b/core/java/android/widget/AbsListView.java
@@ -442,8 +442,10 @@ public abstract class AbsListView extends AdapterView<ListAdapter> implements Te
/**
* Handles one frame of a fling
+ *
+ * To interrupt a fling early you should use smoothScrollBy(0,0) instead
*/
- @UnsupportedAppUsage
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
private FlingRunnable mFlingRunnable;
/**
@@ -1611,15 +1613,6 @@ public abstract class AbsListView extends AdapterView<ListAdapter> implements Te
return false;
}
- /** @hide */
- @Override
- public View findViewByAccessibilityIdTraversal(int accessibilityId) {
- if (accessibilityId == getAccessibilityViewId()) {
- return this;
- }
- return super.findViewByAccessibilityIdTraversal(accessibilityId);
- }
-
/**
* Indicates whether the children's drawing cache is used during a scroll.
* By default, the drawing cache is enabled but this will consume more memory.
@@ -4688,7 +4681,8 @@ public abstract class AbsListView extends AdapterView<ListAdapter> implements Te
mScroller = new OverScroller(getContext());
}
- @UnsupportedAppUsage
+ // Use AbsListView#fling(int) instead
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
void start(int initialVelocity) {
int initialY = initialVelocity < 0 ? Integer.MAX_VALUE : 0;
mLastFlingY = initialY;
@@ -4766,7 +4760,8 @@ public abstract class AbsListView extends AdapterView<ListAdapter> implements Te
postOnAnimation(this);
}
- @UnsupportedAppUsage
+ // To interrupt a fling early you should use smoothScrollBy(0,0) instead
+ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
void endFling() {
mTouchMode = TOUCH_MODE_REST;
diff --git a/core/java/android/widget/Magnifier.java b/core/java/android/widget/Magnifier.java
index d5b1a3d69dfe..249f49956256 100644
--- a/core/java/android/widget/Magnifier.java
+++ b/core/java/android/widget/Magnifier.java
@@ -1013,7 +1013,7 @@ public final class Magnifier {
}
synchronized (mLock) {
mRenderer.destroy();
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
mSurfaceSession.kill();
mHandler.removeCallbacks(mMagnifierUpdater);
if (mBitmap != null) {
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java
index 659b71f51588..d87600125a54 100644
--- a/core/java/android/widget/TextView.java
+++ b/core/java/android/widget/TextView.java
@@ -712,7 +712,7 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
@UnsupportedAppUsage
private ChangeWatcher mChangeWatcher;
- @UnsupportedAppUsage
+ @UnsupportedAppUsage(trackingBug = 123769451)
private ArrayList<TextWatcher> mListeners;
// display attributes
@@ -1055,6 +1055,8 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
int inputType = EditorInfo.TYPE_NULL;
a = theme.obtainStyledAttributes(
attrs, com.android.internal.R.styleable.TextView, defStyleAttr, defStyleRes);
+ saveAttributeDataForStyleable(context, com.android.internal.R.styleable.TextView, attrs, a,
+ defStyleAttr, defStyleRes);
int firstBaselineToTopHeight = -1;
int lastBaselineToBottomHeight = -1;
int lineHeight = -1;
diff --git a/core/java/com/android/internal/os/ZygoteConnection.java b/core/java/com/android/internal/os/ZygoteConnection.java
index 9ba56b8c0f4e..4ac7f5012613 100644
--- a/core/java/com/android/internal/os/ZygoteConnection.java
+++ b/core/java/com/android/internal/os/ZygoteConnection.java
@@ -334,9 +334,14 @@ class ZygoteConnection {
}
}
- private class HiddenApiUsageLogger implements VMRuntime.HiddenApiUsageLogger {
+ private static class HiddenApiUsageLogger implements VMRuntime.HiddenApiUsageLogger {
private final MetricsLogger mMetricsLogger = new MetricsLogger();
+ private static HiddenApiUsageLogger sInstance = new HiddenApiUsageLogger();
+
+ public static HiddenApiUsageLogger getInstance() {
+ return HiddenApiUsageLogger.sInstance;
+ }
public void hiddenApiUsed(String packageName, String signature,
int accessMethod, boolean accessDenied) {
@@ -370,7 +375,7 @@ class ZygoteConnection {
private void handleHiddenApiAccessLogSampleRate(int samplingRate) {
try {
ZygoteInit.setHiddenApiAccessLogSampleRate(samplingRate);
- ZygoteInit.setHiddenApiUsageLogger(new HiddenApiUsageLogger());
+ ZygoteInit.setHiddenApiUsageLogger(HiddenApiUsageLogger.getInstance());
mSocketOutStream.writeInt(0);
} catch (IOException ioe) {
throw new IllegalStateException("Error writing to command socket", ioe);
diff --git a/core/jni/android_util_AssetManager.cpp b/core/jni/android_util_AssetManager.cpp
index 4101c04162af..d493ddfaae13 100644
--- a/core/jni/android_util_AssetManager.cpp
+++ b/core/jni/android_util_AssetManager.cpp
@@ -1105,6 +1105,46 @@ static jobjectArray NativeGetSizeConfigurations(JNIEnv* env, jclass /*clazz*/, j
return array;
}
+static jintArray NativeAttributeResolutionStack(
+ JNIEnv* env, jclass /*clazz*/, jlong ptr,
+ jlong theme_ptr, jint xml_style_res,
+ jint def_style_attr, jint def_style_resid) {
+
+ ScopedLock<AssetManager2> assetmanager(AssetManagerFromLong(ptr));
+ Theme* theme = reinterpret_cast<Theme*>(theme_ptr);
+ CHECK(theme->GetAssetManager() == &(*assetmanager));
+ (void) assetmanager;
+
+ // Load default style from attribute, if specified...
+ uint32_t def_style_flags = 0u;
+ if (def_style_attr != 0) {
+ Res_value value;
+ if (theme->GetAttribute(def_style_attr, &value, &def_style_flags) != kInvalidCookie) {
+ if (value.dataType == Res_value::TYPE_REFERENCE) {
+ def_style_resid = value.data;
+ }
+ }
+ }
+
+ auto style_stack = assetmanager->GetBagResIdStack(xml_style_res);
+ auto def_style_stack = assetmanager->GetBagResIdStack(def_style_resid);
+
+ jintArray array = env->NewIntArray(style_stack.size() + def_style_stack.size());
+ if (env->ExceptionCheck()) {
+ return nullptr;
+ }
+
+ for (uint32_t i = 0; i < style_stack.size(); i++) {
+ jint attr_resid = style_stack[i];
+ env->SetIntArrayRegion(array, i, 1, &attr_resid);
+ }
+ for (uint32_t i = 0; i < def_style_stack.size(); i++) {
+ jint attr_resid = def_style_stack[i];
+ env->SetIntArrayRegion(array, style_stack.size() + i, 1, &attr_resid);
+ }
+ return array;
+}
+
static void NativeApplyStyle(JNIEnv* env, jclass /*clazz*/, jlong ptr, jlong theme_ptr,
jint def_style_attr, jint def_style_resid, jlong xml_parser_ptr,
jintArray java_attrs, jlong out_values_ptr, jlong out_indices_ptr) {
@@ -1456,6 +1496,7 @@ static const JNINativeMethod gAssetManagerMethods[] = {
(void*)NativeGetSizeConfigurations},
// Style attribute related methods.
+ {"nativeAttributeResolutionStack", "(JJIII)[I", (void*)NativeAttributeResolutionStack},
{"nativeApplyStyle", "(JJIIJ[IJJ)V", (void*)NativeApplyStyle},
{"nativeResolveAttrs", "(JJII[I[I[I[I)Z", (void*)NativeResolveAttrs},
{"nativeRetrieveAttributes", "(JJ[I[I[I)Z", (void*)NativeRetrieveAttributes},
diff --git a/core/jni/android_view_Surface.cpp b/core/jni/android_view_Surface.cpp
index 67a56ae2b52d..464f24901eb1 100644
--- a/core/jni/android_view_Surface.cpp
+++ b/core/jni/android_view_Surface.cpp
@@ -58,6 +58,8 @@
namespace android {
+using ui::Dataspace;
+
static const char* const OutOfResourcesException =
"android/view/Surface$OutOfResourcesException";
@@ -132,6 +134,7 @@ int android_view_Surface_mapPublicFormatToHalFormat(PublicFormat f) {
case PublicFormat::JPEG:
case PublicFormat::DEPTH_POINT_CLOUD:
case PublicFormat::DEPTH_JPEG:
+ case PublicFormat::HEIC:
return HAL_PIXEL_FORMAT_BLOB;
case PublicFormat::DEPTH16:
return HAL_PIXEL_FORMAT_Y16;
@@ -146,32 +149,44 @@ int android_view_Surface_mapPublicFormatToHalFormat(PublicFormat f) {
android_dataspace android_view_Surface_mapPublicFormatToHalDataspace(
PublicFormat f) {
+ Dataspace dataspace;
switch(f) {
case PublicFormat::JPEG:
- return HAL_DATASPACE_V0_JFIF;
+ dataspace = Dataspace::V0_JFIF;
+ break;
case PublicFormat::DEPTH_POINT_CLOUD:
case PublicFormat::DEPTH16:
case PublicFormat::RAW_DEPTH:
- return HAL_DATASPACE_DEPTH;
+ dataspace = Dataspace::DEPTH;
+ break;
case PublicFormat::RAW_SENSOR:
case PublicFormat::RAW_PRIVATE:
case PublicFormat::RAW10:
case PublicFormat::RAW12:
- return HAL_DATASPACE_ARBITRARY;
+ dataspace = Dataspace::ARBITRARY;
+ break;
case PublicFormat::YUV_420_888:
case PublicFormat::NV21:
case PublicFormat::YV12:
- return HAL_DATASPACE_V0_JFIF;
+ dataspace = Dataspace::V0_JFIF;
+ break;
case PublicFormat::DEPTH_JPEG:
- return static_cast<android_dataspace> (HAL_DATASPACE_DYNAMIC_DEPTH);
+ dataspace = Dataspace::DYNAMIC_DEPTH;
+ break;
+ case PublicFormat::HEIC:
+ dataspace = Dataspace::HEIF;
+ break;
default:
// Most formats map to UNKNOWN
- return HAL_DATASPACE_UNKNOWN;
+ dataspace = Dataspace::UNKNOWN;
+ break;
}
+ return static_cast<android_dataspace>(dataspace);
}
PublicFormat android_view_Surface_mapHalFormatDataspaceToPublicFormat(
int format, android_dataspace dataSpace) {
+ Dataspace ds = static_cast<Dataspace>(dataSpace);
switch(format) {
case HAL_PIXEL_FORMAT_RGBA_8888:
case HAL_PIXEL_FORMAT_RGBX_8888:
@@ -187,8 +202,8 @@ PublicFormat android_view_Surface_mapHalFormatDataspaceToPublicFormat(
// Enums overlap in both name and value
return static_cast<PublicFormat>(format);
case HAL_PIXEL_FORMAT_RAW16:
- switch (dataSpace) {
- case HAL_DATASPACE_DEPTH:
+ switch (ds) {
+ case Dataspace::DEPTH:
return PublicFormat::RAW_DEPTH;
default:
return PublicFormat::RAW_SENSOR;
@@ -210,8 +225,8 @@ PublicFormat android_view_Surface_mapHalFormatDataspaceToPublicFormat(
return PublicFormat::PRIVATE;
case HAL_PIXEL_FORMAT_Y16:
// Dataspace-dependent
- switch (dataSpace) {
- case HAL_DATASPACE_DEPTH:
+ switch (ds) {
+ case Dataspace::DEPTH:
return PublicFormat::DEPTH16;
default:
// Assume non-depth Y16 is just Y16.
@@ -220,11 +235,13 @@ PublicFormat android_view_Surface_mapHalFormatDataspaceToPublicFormat(
break;
case HAL_PIXEL_FORMAT_BLOB:
// Dataspace-dependent
- switch (dataSpace) {
- case HAL_DATASPACE_DEPTH:
+ switch (ds) {
+ case Dataspace::DEPTH:
return PublicFormat::DEPTH_POINT_CLOUD;
- case HAL_DATASPACE_V0_JFIF:
+ case Dataspace::V0_JFIF:
return PublicFormat::JPEG;
+ case Dataspace::HEIF:
+ return PublicFormat::HEIC;
default:
if (dataSpace == static_cast<android_dataspace>(HAL_DATASPACE_DYNAMIC_DEPTH)) {
return PublicFormat::DEPTH_JPEG;
diff --git a/core/jni/android_view_SurfaceControl.cpp b/core/jni/android_view_SurfaceControl.cpp
index 68be0054ae45..6b8d8b1bb91f 100644
--- a/core/jni/android_view_SurfaceControl.cpp
+++ b/core/jni/android_view_SurfaceControl.cpp
@@ -178,12 +178,13 @@ static jlong nativeCreate(JNIEnv* env, jclass clazz, jobject sessionObj,
static void nativeRelease(JNIEnv* env, jclass clazz, jlong nativeObject) {
sp<SurfaceControl> ctrl(reinterpret_cast<SurfaceControl *>(nativeObject));
+ ctrl->release();
ctrl->decStrong((void *)nativeCreate);
}
static void nativeDestroy(JNIEnv* env, jclass clazz, jlong nativeObject) {
sp<SurfaceControl> ctrl(reinterpret_cast<SurfaceControl *>(nativeObject));
- ctrl->clear();
+ ctrl->destroy();
ctrl->decStrong((void *)nativeCreate);
}
diff --git a/core/jni/include/android_runtime/android_view_Surface.h b/core/jni/include/android_runtime/android_view_Surface.h
index 984e942207c1..3f7c00c9ff01 100644
--- a/core/jni/include/android_runtime/android_view_Surface.h
+++ b/core/jni/include/android_runtime/android_view_Surface.h
@@ -55,10 +55,11 @@ enum class PublicFormat {
DEPTH_POINT_CLOUD = 0x101,
RAW_DEPTH = 0x1002, // @hide
YV12 = 0x32315659,
- Y8 = 0x20203859, // @hide
+ Y8 = 0x20203859,
Y16 = 0x20363159, // @hide
DEPTH16 = 0x44363159,
DEPTH_JPEG = 0x69656963,
+ HEIC = 0x48454946,
};
/* Gets the underlying ANativeWindow for a Surface. */
diff --git a/core/proto/android/providers/settings/global.proto b/core/proto/android/providers/settings/global.proto
index a160451ecfed..d5776534bb90 100644
--- a/core/proto/android/providers/settings/global.proto
+++ b/core/proto/android/providers/settings/global.proto
@@ -259,6 +259,8 @@ message GlobalSettingsProto {
optional SettingProto app = 1;
// Whether views are allowed to save their attribute data.
optional SettingProto view_attributes = 2 [ (android.privacy).dest = DEST_AUTOMATIC ];
+ // Which application package is allowed to save view attribute data.
+ optional SettingProto view_attributes_application_package = 3 [ (android.privacy).dest = DEST_AUTOMATIC ];
}
optional Debug debug = 37;
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index 60b04cf6c77b..07dd26e4969b 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -662,8 +662,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readContacts"
android:description="@string/permdesc_readContacts"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to write the user's contacts data.
<p>Protection level: dangerous
@@ -694,8 +693,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readCalendar"
android:description="@string/permdesc_readCalendar"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to write the user's calendar data.
<p>Protection level: dangerous
@@ -736,8 +734,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_receiveSms"
android:description="@string/permdesc_receiveSms"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to read SMS messages.
<p>Protection level: dangerous
@@ -746,8 +743,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readSms"
android:description="@string/permdesc_readSms"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to receive WAP push messages.
<p>Protection level: dangerous
@@ -756,8 +752,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_receiveWapPush"
android:description="@string/permdesc_receiveWapPush"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to monitor incoming MMS messages.
<p>Protection level: dangerous
@@ -766,8 +761,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_receiveMms"
android:description="@string/permdesc_receiveMms"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- @SystemApi @TestApi Allows an application to read previously received cell broadcast
messages and to register a content observer to get notifications when
@@ -785,8 +779,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readCellBroadcasts"
android:description="@string/permdesc_readCellBroadcasts"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- ====================================================================== -->
<!-- Permissions for accessing external storage -->
@@ -867,8 +860,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_audioRead"
android:description="@string/permdesc_audioRead"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Runtime permission controlling access to the user's shared visual media
collection, including images and videos. -->
@@ -884,16 +876,14 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_imagesRead"
android:description="@string/permdesc_imagesRead"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to read the user's shared video collection. -->
<permission android:name="android.permission.READ_MEDIA_VIDEO"
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_videoRead"
android:description="@string/permdesc_videoRead"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to access any geographic locations persisted in the
user's shared collection. -->
@@ -901,8 +891,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_mediaLocation"
android:description="@string/permdesc_mediaLocation"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- @hide @SystemApi @TestApi
Allows an application to modify OBB files visible to other apps. -->
@@ -934,8 +923,7 @@
android:label="@string/permlab_accessFineLocation"
android:description="@string/permdesc_accessFineLocation"
android:backgroundPermission="android.permission.ACCESS_BACKGROUND_LOCATION"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- Allows an app to access approximate location.
Alternatively, you might want {@link #ACCESS_FINE_LOCATION}.
@@ -946,8 +934,7 @@
android:label="@string/permlab_accessCoarseLocation"
android:description="@string/permdesc_accessCoarseLocation"
android:backgroundPermission="android.permission.ACCESS_BACKGROUND_LOCATION"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- Allows an app to access location in the background. If you
are requesting this, you should also request {@link #ACCESS_FINE_LOCATION}.
@@ -959,8 +946,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_accessBackgroundLocation"
android:description="@string/permdesc_accessBackgroundLocation"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- ====================================================================== -->
<!-- Permissions for accessing the call log -->
@@ -1001,8 +987,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readCallLog"
android:description="@string/permdesc_readCallLog"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an application to write (but not read) the user's
call log data.
@@ -1032,8 +1017,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_processOutgoingCalls"
android:description="@string/permdesc_processOutgoingCalls"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- ====================================================================== -->
<!-- Permissions for accessing the device telephony -->
@@ -1065,8 +1049,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readPhoneState"
android:description="@string/permdesc_readPhoneState"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows read access to the device's phone number(s). This is a subset of the capabilities
granted by {@link #READ_PHONE_STATE} but is exposed to instant applications.
@@ -1075,8 +1058,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_readPhoneNumbers"
android:description="@string/permdesc_readPhoneNumbers"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- Allows an application to initiate a phone call without going through
the Dialer user interface for the user to confirm the call.
@@ -1178,8 +1160,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_recordAudio"
android:description="@string/permdesc_recordAudio"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- ====================================================================== -->
<!-- Permissions for activity recognition -->
@@ -1202,8 +1183,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_activityRecognition"
android:description="@string/permdesc_activityRecognition"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- ====================================================================== -->
<!-- Permissions for accessing the UCE Service -->
@@ -1252,8 +1232,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_camera"
android:description="@string/permdesc_camera"
- android:protectionLevel="dangerous|instant"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous|instant" />
<!-- ====================================================================== -->
@@ -1277,8 +1256,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:label="@string/permlab_bodySensors"
android:description="@string/permdesc_bodySensors"
- android:protectionLevel="dangerous"
- android:usageInfoRequired="true" />
+ android:protectionLevel="dangerous" />
<!-- Allows an app to use fingerprint hardware.
<p>Protection level: normal
@@ -1780,8 +1758,7 @@
android:permissionGroup="android.permission-group.UNDEFINED"
android:protectionLevel="dangerous"
android:description="@string/permdesc_getAccounts"
- android:label="@string/permlab_getAccounts"
- android:usageInfoRequired="true" />
+ android:label="@string/permlab_getAccounts" />
<uses-permission android:name="android.permission.GET_ACCOUNTS"/>
<!-- Allows applications to call into AccountAuthenticators.
diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml
index fa3a549463f5..46e14b41960c 100644
--- a/core/res/res/values/attrs.xml
+++ b/core/res/res/values/attrs.xml
@@ -2426,6 +2426,8 @@
</attr>
<attr name="__removed3" />
+ <attr name="__removed4" />
+ <attr name="__removed5" />
<!-- Describes the content of a view so that a autofill service can fill in the appropriate
data. Multiple hints can be combined in a comma separated list or an array of strings
diff --git a/core/res/res/values/attrs_manifest.xml b/core/res/res/values/attrs_manifest.xml
index 881688bd00c0..53cae638db80 100644
--- a/core/res/res/values/attrs_manifest.xml
+++ b/core/res/res/values/attrs_manifest.xml
@@ -1689,10 +1689,6 @@
<attr name="request" />
<attr name="protectionLevel" />
<attr name="permissionFlags" />
- <!-- If {@code true} applications that target Q <em>must</em> specify the permission usage
- attributes in their {@code uses-permission} elements or the permission will not be
- granted. -->
- <attr name="usageInfoRequired" format="boolean" />
</declare-styleable>
<!-- The <code>permission-group</code> tag declares a logical grouping of
@@ -1792,81 +1788,6 @@
requested. If it does support the feature, it will be as if the manifest didn't
request it at all. -->
<attr name="requiredNotFeature" format="string" />
-
- <!-- Specify if the app uploads data, or derived data, guarded by this permission.
-
- If the permission is defined with {@link android.R.attr#usageInfoRequired}
- {@code true} this <em>must</em> be specified by apps that target Android Q or the
- permission will not be granted, it will be as if the manifest didn't request it at all.
- -->
- <attr name="dataSentOffDevice">
- <!-- The application may send data, or derived data, guarded by this permission off of the
- device. -->
- <enum name="yes" value="1" />
- <!-- The application may send data, or derived data, guarded by this permission off of the
- device, however it will only do so when explicitly triggered by a user action. -->
- <enum name="userTriggered" value="2" />
- <!-- The application does not send data, or derived data, guarded by this permission off
- of the device. -->
- <enum name="no" value="3" />
- </attr>
-
- <!-- Specify if the application or its related off-device services provide data,
- or derived data, guarded by this permission to third parties outside of the developer's
- organization that do not qualify as data processors.
-
- If the permission is defined with {@link android.R.attr#usageInfoRequired}
- {@code true} this <em>must</em> be specified by apps that target Android Q or the
- permission will not be granted, it will be as if the manifest didn't request it at all.
- -->
- <attr name="dataSharedWithThirdParty">
- <!-- The application or its services may provide data, or derived data, guarded by this
- permission to third party organizations. -->
- <enum name="yes" value="1" />
- <!-- The application or its services may provide data, or derived data, guarded by this
- permission to third party organizations, however it will only do so when explicitly
- triggered by a user action. -->
- <enum name="userTriggered" value="2" />
- <!-- The application or its services does not provide data, or derived data, guarded by
- this permission to third party organizations. -->
- <enum name="no" value="3" />
- </attr>
-
- <!-- Specify if the application or its related off-device services use data,
- or derived data, guarded by this permission for monetization purposes.
-
- For example, if the data is sold to another party or used for targeting advertisements
- this must be set to {@code yes}.
-
- If the permission is defined with {@link android.R.attr#usageInfoRequired}
- {@code true} this <em>must</em> be specified by apps that target Android Q or the
- permission will not be granted, it will be as if the manifest didn't request it at all.
- -->
- <attr name="dataUsedForMonetization">
- <!-- The application or its services may use data, or derived data, guarded by this
- permission for monetization purposes. -->
- <enum name="yes" value="1" />
- <!-- The application or its services may use data, or derived data, guarded by this
- permission for monetization purposes, however it will only do so when explicity
- triggered by a user action. -->
- <enum name="userTriggered" value="2" />
- <!-- The application or its services does not use data, or derived data, guarded by
- this permission for monetization purposes. -->
- <enum name="no" value="3" />
- </attr>
-
- <!-- Specify how long the application or its related off-device services store
- data, or derived data, guarded by this permission.
-
- This can be one of "notRetained", "userSelected", "unlimited", or a number
- representing the number of weeks the data is retained.
-
- If the permission is defined with {@link android.R.attr#usageInfoRequired}
- {@code true} this <em>must</em> be specified by apps that target Android Q or the
- permission will not be granted, it will be as if the manifest didn't request it at all.
- -->
- <attr name="dataRetentionTime" format="string" />
-
</declare-styleable>
<!-- The <code>uses-configuration</code> tag specifies
diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml
index 76b589ca4009..ec53811a6983 100644
--- a/core/res/res/values/config.xml
+++ b/core/res/res/values/config.xml
@@ -963,7 +963,7 @@
<bool name="config_nightDisplayAvailable">@bool/config_setColorTransformAccelerated</bool>
<!-- Default mode to control how Night display is automatically activated.
- One of the following values (see ColorDisplayController.java):
+ One of the following values (see ColorDisplayManager.java):
0 - AUTO_MODE_DISABLED
1 - AUTO_MODE_CUSTOM_TIME
2 - AUTO_MODE_TWILIGHT
@@ -1052,7 +1052,7 @@
</string-array>
- <!-- Indicate available ColorDisplayController.COLOR_MODE_xxx. -->
+ <!-- Indicate available ColorDisplayManager.COLOR_MODE_xxx. -->
<integer-array name="config_availableColorModes">
<!-- Example:
<item>0</item>
diff --git a/core/res/res/values/public.xml b/core/res/res/values/public.xml
index f84f1f1bdb4f..e6d478aadae0 100644
--- a/core/res/res/values/public.xml
+++ b/core/res/res/values/public.xml
@@ -2925,11 +2925,11 @@
<public name="importantForContentCapture" />
<public name="supportsMultipleDisplays" />
<public name="useAppZygote" />
- <public name="usageInfoRequired" />
- <public name="dataSentOffDevice" />
- <public name="dataSharedWithThirdParty" />
- <public name="dataUsedForMonetization" />
- <public name="dataRetentionTime" />
+ <public name="__removed1" />
+ <public name="__removed2" />
+ <public name="__removed3" />
+ <public name="__removed4" />
+ <public name="__removed5" />
<public name="selectionDividerHeight" />
<public name="foregroundServiceType" />
<public name="hasFragileUserData" />
diff --git a/core/tests/coretests/src/android/provider/SettingsBackupTest.java b/core/tests/coretests/src/android/provider/SettingsBackupTest.java
index 2cb925aa9549..ec57f793f15f 100644
--- a/core/tests/coretests/src/android/provider/SettingsBackupTest.java
+++ b/core/tests/coretests/src/android/provider/SettingsBackupTest.java
@@ -210,6 +210,7 @@ public class SettingsBackupTest {
Settings.Global.DATA_STALL_VALID_DNS_TIME_THRESHOLD,
Settings.Global.DEBUG_APP,
Settings.Global.DEBUG_VIEW_ATTRIBUTES,
+ Settings.Global.DEBUG_VIEW_ATTRIBUTES_APPLICATION_PACKAGE,
Settings.Global.DEFAULT_DNS_SERVER,
Settings.Global.DEFAULT_INSTALL_LOCATION,
Settings.Global.DEFAULT_RESTRICT_BACKGROUND_DATA,
diff --git a/core/tests/coretests/src/android/view/accessibility/FindViewByIdTest.java b/core/tests/coretests/src/android/view/accessibility/FindViewByIdTest.java
new file mode 100644
index 000000000000..da6ecb45bd5c
--- /dev/null
+++ b/core/tests/coretests/src/android/view/accessibility/FindViewByIdTest.java
@@ -0,0 +1,100 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.view.accessibility;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNull;
+
+import android.app.Activity;
+import android.content.Context;
+import android.view.View;
+import android.widget.LinearLayout;
+
+import androidx.test.InstrumentationRegistry;
+import androidx.test.annotation.UiThreadTest;
+import androidx.test.filters.MediumTest;
+import androidx.test.rule.ActivityTestRule;
+
+import org.junit.Rule;
+import org.junit.Test;
+
+@MediumTest
+public class FindViewByIdTest {
+
+ @Rule
+ public ActivityTestRule<Activity> mActivityRule = new ActivityTestRule<>(Activity.class);
+
+ private Context getContext() {
+ return InstrumentationRegistry.getTargetContext();
+ }
+
+ private Activity getActivity() {
+ return mActivityRule.getActivity();
+ }
+
+ @UiThreadTest
+ @Test
+ public void testFindViewById() {
+ LinearLayout contentView = new LinearLayout(getContext());
+ getActivity().setContentView(contentView);
+ View child1 = new View(getContext());
+ View child2 = new View(getContext());
+ child1.setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+ child2.setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+
+ contentView.addView(child1);
+ contentView.addView(child2);
+ View result = AccessibilityNodeIdManager.getInstance().findView(
+ child2.getAccessibilityViewId());
+ assertEquals(result, child2);
+ }
+
+ @UiThreadTest
+ @Test
+ public void testFindViewByIdReturnNullIfRemovedFromHierarchy() {
+ LinearLayout contentView = new LinearLayout(getContext());
+ getActivity().setContentView(contentView);
+ View child1 = new View(getContext());
+ View child2 = new View(getContext());
+ contentView.addView(child1);
+ contentView.addView(child2);
+ child1.setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+ child2.setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+
+ contentView.removeView(child1);
+ View result = AccessibilityNodeIdManager.getInstance().findView(
+ child1.getAccessibilityViewId());
+ assertNull(result);
+ }
+
+ @UiThreadTest
+ @Test
+ public void testFindViewByIdReturnNullIfNotImportant() {
+ LinearLayout contentView = new LinearLayout(getContext());
+ getActivity().setContentView(contentView);
+ View child1 = new View(getContext());
+ View child2 = new View(getContext());
+ child2.setImportantForAccessibility(View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+
+ contentView.addView(child1);
+ contentView.addView(child2);
+
+ View result = AccessibilityNodeIdManager.getInstance().findView(
+ child1.getAccessibilityViewId());
+ assertNull(result);
+ }
+}
diff --git a/core/tests/coretests/src/android/view/contentcapture/ContentCaptureEventTest.java b/core/tests/coretests/src/android/view/contentcapture/ContentCaptureEventTest.java
new file mode 100644
index 000000000000..f325d8943ea3
--- /dev/null
+++ b/core/tests/coretests/src/android/view/contentcapture/ContentCaptureEventTest.java
@@ -0,0 +1,229 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package android.view.contentcapture;
+
+import static android.view.contentcapture.ContentCaptureEvent.TYPE_SESSION_FINISHED;
+import static android.view.contentcapture.ContentCaptureEvent.TYPE_SESSION_STARTED;
+import static android.view.contentcapture.ContentCaptureEvent.TYPE_VIEW_DISAPPEARED;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.testng.Assert.assertThrows;
+
+import android.os.Parcel;
+import android.os.SystemClock;
+import android.view.autofill.AutofillId;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.JUnit4;
+
+import java.util.ArrayList;
+
+/**
+ * Unit test for {@link ContentCaptureEvent}.
+ *
+ * <p>To run it:
+ * {@code atest FrameworksCoreTests:android.view.contentcapture.ContentCaptureEventTest}
+ */
+@RunWith(JUnit4.class)
+public class ContentCaptureEventTest {
+
+ private static final long MY_EPOCH = SystemClock.uptimeMillis();
+
+ // Not using @Mock because it's final - no need to be fancy here....
+ private final ContentCaptureContext mClientContext = new ContentCaptureContext.Builder()
+ .setAction("WHATEVER").build();
+
+ @Test
+ public void testSetAutofillId_null() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ assertThrows(NullPointerException.class, () -> event.setAutofillId(null));
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).isNull();
+ }
+
+ @Test
+ public void testSetAutofillIds_null() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ assertThrows(NullPointerException.class, () -> event.setAutofillIds(null));
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).isNull();
+ }
+
+ @Test
+ public void testAddAutofillId_null() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ assertThrows(NullPointerException.class, () -> event.addAutofillId(null));
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).isNull();
+ }
+
+ @Test
+ public void testSetAutofillId() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ final AutofillId id = new AutofillId(108);
+ event.setAutofillId(id);
+ assertThat(event.getId()).isEqualTo(id);
+ assertThat(event.getIds()).isNull();
+ }
+
+ @Test
+ public void testSetAutofillIds() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ final AutofillId id = new AutofillId(108);
+ final ArrayList<AutofillId> ids = new ArrayList<>(1);
+ ids.add(id);
+ event.setAutofillIds(ids);
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).containsExactly(id);
+ }
+
+ @Test
+ public void testAddAutofillId() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ final AutofillId id1 = new AutofillId(108);
+ event.addAutofillId(id1);
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).containsExactly(id1);
+
+ final AutofillId id2 = new AutofillId(666);
+ event.addAutofillId(id2);
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).containsExactly(id1, id2).inOrder();
+ }
+
+ @Test
+ public void testAddAutofillId_afterSetId() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ final AutofillId id1 = new AutofillId(108);
+ event.setAutofillId(id1);
+ assertThat(event.getId()).isEqualTo(id1);
+ assertThat(event.getIds()).isNull();
+
+ final AutofillId id2 = new AutofillId(666);
+ event.addAutofillId(id2);
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).containsExactly(id1, id2).inOrder();
+ }
+
+ @Test
+ public void testAddAutofillId_afterSetIds() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_VIEW_DISAPPEARED);
+
+ final AutofillId id1 = new AutofillId(108);
+ final ArrayList<AutofillId> ids = new ArrayList<>(1);
+ ids.add(id1);
+ event.setAutofillIds(ids);
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).containsExactly(id1);
+
+ final AutofillId id2 = new AutofillId(666);
+ event.addAutofillId(id2);
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).containsExactly(id1, id2).inOrder();
+ }
+
+ @Test
+ public void testSessionStarted_directly() {
+ final ContentCaptureEvent event = newEventForSessionStarted();
+ assertSessionStartedEvent(event);
+ }
+
+ @Test
+ public void testSessionStarted_throughParcel() {
+ final ContentCaptureEvent event = newEventForSessionStarted();
+ final ContentCaptureEvent clone = cloneThroughParcel(event);
+ assertSessionStartedEvent(clone);
+ }
+
+ private ContentCaptureEvent newEventForSessionStarted() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_SESSION_STARTED)
+ .setClientContext(mClientContext)
+ .setParentSessionId("108");
+ assertThat(event).isNotNull();
+ return event;
+ }
+
+ private void assertSessionStartedEvent(ContentCaptureEvent event) {
+ assertThat(event.getType()).isEqualTo(TYPE_SESSION_STARTED);
+ assertThat(event.getEventTime()).isAtLeast(MY_EPOCH);
+ assertThat(event.getSessionId()).isEqualTo("42");
+ assertThat(event.getParentSessionId()).isEqualTo("108");
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).isNull();
+ assertThat(event.getText()).isNull();
+ assertThat(event.getViewNode()).isNull();
+ final ContentCaptureContext clientContext = event.getClientContext();
+ assertThat(clientContext.getAction()).isEqualTo("WHATEVER");
+ }
+
+ @Test
+ public void testSessionFinished_directly() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_SESSION_FINISHED)
+ .setParentSessionId("108");
+ assertThat(event).isNotNull();
+ assertSessionFinishedEvent(event);
+ }
+
+ @Test
+ public void testSessionFinished_throughParcel() {
+ final ContentCaptureEvent event = new ContentCaptureEvent("42", TYPE_SESSION_FINISHED)
+ .setClientContext(mClientContext) // should not be writting to parcel
+ .setParentSessionId("108");
+ assertThat(event).isNotNull();
+ final ContentCaptureEvent clone = cloneThroughParcel(event);
+ assertSessionFinishedEvent(clone);
+ }
+
+ private void assertSessionFinishedEvent(ContentCaptureEvent event) {
+ assertThat(event.getType()).isEqualTo(TYPE_SESSION_FINISHED);
+ assertThat(event.getEventTime()).isAtLeast(MY_EPOCH);
+ assertThat(event.getSessionId()).isEqualTo("42");
+ assertThat(event.getParentSessionId()).isEqualTo("108");
+ assertThat(event.getId()).isNull();
+ assertThat(event.getIds()).isNull();
+ assertThat(event.getText()).isNull();
+ assertThat(event.getViewNode()).isNull();
+ assertThat(event.getClientContext()).isNull();
+ }
+
+ private ContentCaptureEvent cloneThroughParcel(ContentCaptureEvent event) {
+ Parcel parcel = Parcel.obtain();
+
+ try {
+ // Write to parcel
+ parcel.setDataPosition(0); // Sanity / paranoid check
+ event.writeToParcel(parcel, 0);
+
+ // Read from parcel
+ parcel.setDataPosition(0);
+ ContentCaptureEvent clone = ContentCaptureEvent.CREATOR.createFromParcel(parcel);
+ assertThat(clone).isNotNull();
+ return clone;
+ } finally {
+ parcel.recycle();
+ }
+ }
+
+}
diff --git a/core/tests/coretests/src/android/view/contentcapture/UserDataRemovalRequestTest.java b/core/tests/coretests/src/android/view/contentcapture/UserDataRemovalRequestTest.java
deleted file mode 100644
index bebb2a89f480..000000000000
--- a/core/tests/coretests/src/android/view/contentcapture/UserDataRemovalRequestTest.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package android.view.contentcapture;
-
-import static com.google.common.truth.Truth.assertThat;
-
-import static org.testng.Assert.assertThrows;
-
-import android.net.Uri;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mock;
-import org.mockito.junit.MockitoJUnitRunner;
-
-/**
- * Unit test for {@link UserDataRemovalRequest}.
- *
- * <p>To run it:
- * {@code atest FrameworksCoreTests:android.view.contentcapture.UserDataRemovalRequestTest}
- */
-@RunWith(MockitoJUnitRunner.class)
-public class UserDataRemovalRequestTest {
-
- @Mock
- private final Uri mUri = Uri.parse("content://com.example/");
-
- private UserDataRemovalRequest.Builder mBuilder = new UserDataRemovalRequest.Builder();
-
- @Test
- public void testBuilder_addUri_invalid() {
- assertThrows(NullPointerException.class, () -> mBuilder.addUri(null, false));
- }
-
- @Test
- public void testBuilder_addUri_valid() {
- assertThat(mBuilder.addUri(mUri, false)).isNotNull();
- assertThat(mBuilder.addUri(Uri.parse("content://com.example2"), true)).isNotNull();
- }
-
- @Test
- public void testBuilder_addUriAfterForEverything() {
- assertThat(mBuilder.forEverything()).isNotNull();
- assertThrows(IllegalStateException.class, () -> mBuilder.addUri(mUri, false));
- }
-
- @Test
- public void testBuilder_forEverythingAfterAddingUri() {
- assertThat(mBuilder.addUri(mUri, false)).isNotNull();
- assertThrows(IllegalStateException.class, () -> mBuilder.forEverything());
- }
-
- @Test
- public void testBuild_invalid() {
- assertThrows(IllegalStateException.class, () -> mBuilder.build());
- }
-
- @Test
- public void testBuild_valid() {
- assertThat(new UserDataRemovalRequest.Builder().forEverything().build())
- .isNotNull();
- assertThat(new UserDataRemovalRequest.Builder().addUri(mUri, false).build())
- .isNotNull();
- }
-
- @Test
- public void testNoMoreInteractionsAfterBuild() {
- assertThat(mBuilder.forEverything().build()).isNotNull();
-
- assertThrows(IllegalStateException.class, () -> mBuilder.addUri(mUri, false));
- assertThrows(IllegalStateException.class, () -> mBuilder.forEverything());
- assertThrows(IllegalStateException.class, () -> mBuilder.build());
-
- }
-}
diff --git a/core/tests/coretests/src/android/view/contentcapture/ViewNodeTest.java b/core/tests/coretests/src/android/view/contentcapture/ViewNodeTest.java
index b84a098574c2..213cd405e903 100644
--- a/core/tests/coretests/src/android/view/contentcapture/ViewNodeTest.java
+++ b/core/tests/coretests/src/android/view/contentcapture/ViewNodeTest.java
@@ -18,29 +18,18 @@ package android.view.contentcapture;
import static com.google.common.truth.Truth.assertThat;
-import static org.testng.Assert.assertThrows;
-
import android.content.Context;
import android.graphics.Matrix;
-import android.os.Bundle;
-import android.os.LocaleList;
-import android.os.Parcel;
+import android.support.test.InstrumentationRegistry;
import android.view.View;
import android.view.ViewStructure.HtmlInfo;
-import android.view.autofill.AutofillId;
-import android.view.autofill.AutofillValue;
import android.view.contentcapture.ViewNode.ViewStructureImpl;
-import android.widget.FrameLayout;
-
-import androidx.test.InstrumentationRegistry;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.junit.MockitoJUnitRunner;
-import java.util.Locale;
-
/**
* Unit tests for {@link ViewNode}.
*
@@ -55,100 +44,6 @@ public class ViewNodeTest {
private HtmlInfo mHtmlInfoMock;
@Test
- public void testAutofillIdMethods_orphanView() {
- View view = new View(mContext);
- AutofillId initialId = new AutofillId(42);
- view.setAutofillId(initialId);
-
- ViewStructureImpl structure = new ViewStructureImpl(view);
- ViewNode node = structure.getNode();
-
- assertThat(node.getAutofillId()).isEqualTo(initialId);
- assertThat(node.getParentAutofillId()).isNull();
-
- AutofillId newId = new AutofillId(108);
- structure.setAutofillId(newId);
- assertThat(node.getAutofillId()).isEqualTo(newId);
- assertThat(node.getParentAutofillId()).isNull();
-
- structure.setAutofillId(new AutofillId(66), 6);
- assertThat(node.getAutofillId()).isEqualTo(new AutofillId(66, 6));
- assertThat(node.getParentAutofillId()).isEqualTo(new AutofillId(66));
- }
-
- @Test
- public void testAutofillIdMethods_parentedView() {
- FrameLayout parent = new FrameLayout(mContext);
- AutofillId initialParentId = new AutofillId(48);
- parent.setAutofillId(initialParentId);
-
- View child = new View(mContext);
- AutofillId initialChildId = new AutofillId(42);
- child.setAutofillId(initialChildId);
-
- parent.addView(child);
-
- ViewStructureImpl structure = new ViewStructureImpl(child);
- ViewNode node = structure.getNode();
-
- assertThat(node.getAutofillId()).isEqualTo(initialChildId);
- assertThat(node.getParentAutofillId()).isEqualTo(initialParentId);
-
- AutofillId newChildId = new AutofillId(108);
- structure.setAutofillId(newChildId);
- assertThat(node.getAutofillId()).isEqualTo(newChildId);
- assertThat(node.getParentAutofillId()).isEqualTo(initialParentId);
-
- AutofillId newParentId = new AutofillId(15162342);
- parent.setAutofillId(newParentId);
- assertThat(node.getAutofillId()).isEqualTo(newChildId);
- assertThat(node.getParentAutofillId()).isEqualTo(initialParentId);
-
- structure.setAutofillId(new AutofillId(66), 6);
- assertThat(node.getAutofillId()).isEqualTo(new AutofillId(66, 6));
- assertThat(node.getParentAutofillId()).isEqualTo(new AutofillId(66));
- }
-
- @Test
- public void testAutofillIdMethods_explicitIdsConstructor() {
- AutofillId initialParentId = new AutofillId(42);
- ViewStructureImpl structure = new ViewStructureImpl(initialParentId, 108, 666);
- ViewNode node = structure.getNode();
-
- assertThat(node.getAutofillId()).isEqualTo(new AutofillId(initialParentId, 108, 666));
- assertThat(node.getParentAutofillId()).isEqualTo(initialParentId);
-
- AutofillId newChildId = new AutofillId(108);
- structure.setAutofillId(newChildId);
- assertThat(node.getAutofillId()).isEqualTo(newChildId);
- assertThat(node.getParentAutofillId()).isEqualTo(initialParentId);
-
- structure.setAutofillId(new AutofillId(66), 6);
- assertThat(node.getAutofillId()).isEqualTo(new AutofillId(66, 6));
- assertThat(node.getParentAutofillId()).isEqualTo(new AutofillId(66));
- }
-
- @Test
- public void testInvalidSetters() {
- View view = new View(mContext);
- AutofillId initialId = new AutofillId(42);
- view.setAutofillId(initialId);
-
- ViewStructureImpl structure = new ViewStructureImpl(view);
- ViewNode node = structure.getNode();
- assertThat(node.getAutofillId()).isEqualTo(initialId); // sanity check
-
- assertThrows(NullPointerException.class, () -> structure.setAutofillId(null));
- assertThat(node.getAutofillId()).isEqualTo(initialId); // invariant
-
- assertThrows(NullPointerException.class, () -> structure.setAutofillId(null, 666));
- assertThat(node.getAutofillId()).isEqualTo(initialId); // invariant
-
- assertThrows(NullPointerException.class, () -> structure.setTextIdEntry(null));
- assertThat(node.getTextIdEntry()).isNull();
- }
-
- @Test
public void testUnsupportedProperties() {
View view = new View(mContext);
@@ -190,273 +85,4 @@ public class ViewNodeTest {
structure.setTransformation(Matrix.IDENTITY_MATRIX);
assertThat(node.getTransformation()).isNull();
}
-
- @Test
- public void testValidProperties_directly() {
- ViewStructureImpl structure = newSimpleStructure();
- assertSimpleStructure(structure);
- assertSimpleNode(structure.getNode());
- }
-
- @Test
- public void testValidProperties_throughParcel() {
- ViewStructureImpl structure = newSimpleStructure();
- final ViewNode node = structure.getNode();
- assertSimpleNode(node); // sanity check
-
- final ViewNode clone = cloneThroughParcel(node);
- assertSimpleNode(clone);
- }
-
- @Test
- public void testComplexText_directly() {
- ViewStructureImpl structure = newStructureWithComplexText();
- assertStructureWithComplexText(structure);
- assertNodeWithComplexText(structure.getNode());
- }
-
- @Test
- public void testComplexText_throughParcel() {
- ViewStructureImpl structure = newStructureWithComplexText();
- final ViewNode node = structure.getNode();
- assertNodeWithComplexText(node); // sanity check
-
- ViewNode clone = cloneThroughParcel(node);
- assertNodeWithComplexText(clone);
- }
-
- @Test
- public void testVisibility() {
- // Visibility is a special case becase it use flag masks, so we want to make sure it works
- // fine
- View view = new View(mContext);
- ViewStructureImpl structure = new ViewStructureImpl(view);
- ViewNode node = structure.getNode();
-
- structure.setVisibility(View.VISIBLE);
- assertThat(node.getVisibility()).isEqualTo(View.VISIBLE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.VISIBLE);
-
- structure.setVisibility(View.GONE);
- assertThat(node.getVisibility()).isEqualTo(View.GONE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.GONE);
-
- structure.setVisibility(View.VISIBLE);
- assertThat(node.getVisibility()).isEqualTo(View.VISIBLE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.VISIBLE);
-
- structure.setVisibility(View.INVISIBLE);
- assertThat(node.getVisibility()).isEqualTo(View.INVISIBLE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.INVISIBLE);
-
- structure.setVisibility(View.INVISIBLE | View.GONE);
- assertThat(node.getVisibility()).isEqualTo(View.INVISIBLE | View.GONE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.INVISIBLE | View.GONE);
-
-
- final int invalidValue = Math.max(Math.max(View.VISIBLE, View.INVISIBLE), View.GONE) * 2;
- structure.setVisibility(View.VISIBLE);
- structure.setVisibility(invalidValue); // should be ignored
- assertThat(node.getVisibility()).isEqualTo(View.VISIBLE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.VISIBLE);
-
- structure.setVisibility(View.GONE | invalidValue);
- assertThat(node.getVisibility()).isEqualTo(View.GONE);
- assertThat(cloneThroughParcel(node).getVisibility()).isEqualTo(View.GONE);
- }
-
- /**
- * Creates a {@link ViewStructureImpl} that can be asserted through
- * {@link #assertSimpleNode(ViewNode)}.
- */
- private ViewStructureImpl newSimpleStructure() {
- View view = new View(mContext);
- view.setAutofillId(new AutofillId(42));
-
- ViewStructureImpl structure = new ViewStructureImpl(view);
-
- // Basic properties
- structure.setText("Text is set!");
- structure.setClassName("Classy!");
- structure.setContentDescription("Described I am!");
- structure.setVisibility(View.INVISIBLE);
-
- // Autofill properties
- structure.setAutofillType(View.AUTOFILL_TYPE_TEXT);
- structure.setAutofillHints(new String[] { "Auto", "Man" });
- structure.setAutofillOptions(new String[] { "Maybe" });
- structure.setAutofillValue(AutofillValue.forText("Malkovich"));
-
- // Extra text properties
- structure.setMinTextEms(6);
- structure.setMaxTextLength(66);
- structure.setMaxTextEms(666);
- structure.setInputType(42);
- structure.setTextIdEntry("TEXT, Y U NO ENTRY?");
- structure.setLocaleList(new LocaleList(Locale.US, Locale.ENGLISH));
-
- // Resource id
- structure.setId(16, "package.name", "type.name", "entry.name");
-
- // Dimensions
- structure.setDimens(4, 8, 15, 16, 23, 42);
-
- // Boolean properties
- structure.setAssistBlocked(true);
- structure.setEnabled(true);
- structure.setClickable(true);
- structure.setLongClickable(true);
- structure.setContextClickable(true);
- structure.setFocusable(true);
- structure.setFocused(true);
- structure.setAccessibilityFocused(true);
- structure.setChecked(true);
- structure.setActivated(true);
- structure.setOpaque(true);
-
- // Bundle
- assertThat(structure.hasExtras()).isFalse();
- final Bundle bundle = structure.getExtras();
- assertThat(bundle).isNotNull();
- bundle.putString("Marlon", "Bundle");
- assertThat(structure.hasExtras()).isTrue();
- return structure;
- }
-
- /**
- * Asserts the properties of a {@link ViewNode} that was created by
- * {@link #newSimpleStructure()}.
- */
- private void assertSimpleNode(ViewNode node) {
-
- // Basic properties
- assertThat(node.getAutofillId()).isEqualTo(new AutofillId(42));
- assertThat(node.getParentAutofillId()).isNull();
- assertThat(node.getText()).isEqualTo("Text is set!");
- assertThat(node.getClassName()).isEqualTo("Classy!");
- assertThat(node.getContentDescription().toString()).isEqualTo("Described I am!");
- assertThat(node.getVisibility()).isEqualTo(View.INVISIBLE);
-
- // Autofill properties
- assertThat(node.getAutofillType()).isEqualTo(View.AUTOFILL_TYPE_TEXT);
- assertThat(node.getAutofillHints()).asList().containsExactly("Auto", "Man").inOrder();
- assertThat(node.getAutofillOptions()).asList().containsExactly("Maybe").inOrder();
- assertThat(node.getAutofillValue().getTextValue()).isEqualTo("Malkovich");
-
- // Extra text properties
- assertThat(node.getMinTextEms()).isEqualTo(6);
- assertThat(node.getMaxTextLength()).isEqualTo(66);
- assertThat(node.getMaxTextEms()).isEqualTo(666);
- assertThat(node.getInputType()).isEqualTo(42);
- assertThat(node.getTextIdEntry()).isEqualTo("TEXT, Y U NO ENTRY?");
- assertThat(node.getLocaleList()).isEqualTo(new LocaleList(Locale.US, Locale.ENGLISH));
-
- // Resource id
- assertThat(node.getId()).isEqualTo(16);
- assertThat(node.getIdPackage()).isEqualTo("package.name");
- assertThat(node.getIdType()).isEqualTo("type.name");
- assertThat(node.getIdEntry()).isEqualTo("entry.name");
-
- // Dimensions
- assertThat(node.getLeft()).isEqualTo(4);
- assertThat(node.getTop()).isEqualTo(8);
- assertThat(node.getScrollX()).isEqualTo(15);
- assertThat(node.getScrollY()).isEqualTo(16);
- assertThat(node.getWidth()).isEqualTo(23);
- assertThat(node.getHeight()).isEqualTo(42);
-
- // Boolean properties
- assertThat(node.isAssistBlocked()).isTrue();
- assertThat(node.isEnabled()).isTrue();
- assertThat(node.isClickable()).isTrue();
- assertThat(node.isLongClickable()).isTrue();
- assertThat(node.isContextClickable()).isTrue();
- assertThat(node.isFocusable()).isTrue();
- assertThat(node.isFocused()).isTrue();
- assertThat(node.isAccessibilityFocused()).isTrue();
- assertThat(node.isChecked()).isTrue();
- assertThat(node.isActivated()).isTrue();
- assertThat(node.isOpaque()).isTrue();
-
- // Bundle
- final Bundle bundle = node.getExtras();
- assertThat(bundle).isNotNull();
- assertThat(bundle.size()).isEqualTo(1);
- assertThat(bundle.getString("Marlon")).isEqualTo("Bundle");
- }
-
- /**
- * Asserts the properties of a {@link ViewStructureImpl} that was created by
- * {@link #newSimpleStructure()}.
- */
- private void assertSimpleStructure(ViewStructureImpl structure) {
- assertThat(structure.getAutofillId()).isEqualTo(new AutofillId(42));
- assertThat(structure.getText()).isEqualTo("Text is set!");
-
- // Bundle
- final Bundle bundle = structure.getExtras();
- assertThat(bundle.size()).isEqualTo(1);
- assertThat(bundle.getString("Marlon")).isEqualTo("Bundle");
- }
-
- /**
- * Creates a {@link ViewStructureImpl} with "complex" text properties (such as selection); it
- * can be asserted through {@link #assertNodeWithComplexText(ViewNode)}.
- */
- private ViewStructureImpl newStructureWithComplexText() {
- View view = new View(mContext);
- ViewStructureImpl structure = new ViewStructureImpl(view);
- structure.setText("IGNORE ME!");
- structure.setText("Now we're talking!", 4, 8);
- structure.setHint("Soylent Green is SPOILER ALERT");
- structure.setTextStyle(15.0f, 16, 23, 42);
- structure.setTextLines(new int[] {4, 8, 15} , new int[] {16, 23, 42});
- return structure;
- }
-
- /**
- * Asserts the properties of a {@link ViewNode} that was created by
- * {@link #newStructureWithComplexText()}.
- */
- private void assertNodeWithComplexText(ViewNode node) {
- assertThat(node.getText()).isEqualTo("Now we're talking!");
- assertThat(node.getTextSelectionStart()).isEqualTo(4);
- assertThat(node.getTextSelectionEnd()).isEqualTo(8);
- assertThat(node.getHint()).isEqualTo("Soylent Green is SPOILER ALERT");
- assertThat(node.getTextSize()).isWithin(1.0e-10f).of(15.0f);
- assertThat(node.getTextColor()).isEqualTo(16);
- assertThat(node.getTextBackgroundColor()).isEqualTo(23);
- assertThat(node.getTextStyle()).isEqualTo(42);
- assertThat(node.getTextLineCharOffsets()).asList().containsExactly(4, 8, 15).inOrder();
- assertThat(node.getTextLineBaselines()).asList().containsExactly(16, 23, 42).inOrder();
- }
-
- /**
- * Asserts the properties of a {@link ViewStructureImpl} that was created by
- * {@link #newStructureWithComplexText()}.
- */
- private void assertStructureWithComplexText(ViewStructureImpl structure) {
- assertThat(structure.getText()).isEqualTo("Now we're talking!");
- assertThat(structure.getTextSelectionStart()).isEqualTo(4);
- assertThat(structure.getTextSelectionEnd()).isEqualTo(8);
- assertThat(structure.getHint()).isEqualTo("Soylent Green is SPOILER ALERT");
- }
-
- private ViewNode cloneThroughParcel(ViewNode node) {
- Parcel parcel = Parcel.obtain();
-
- try {
- // Write to parcel
- parcel.setDataPosition(0); // Sanity / paranoid check
- ViewNode.writeToParcel(parcel, node, 0);
-
- // Read from parcel
- parcel.setDataPosition(0);
- ViewNode clone = ViewNode.readFromParcel(parcel);
- assertThat(clone).isNotNull();
- return clone;
- } finally {
- parcel.recycle();
- }
- }
}
diff --git a/data/etc/privapp-permissions-platform.xml b/data/etc/privapp-permissions-platform.xml
index 0f35918232b4..6770ae19ce3d 100644
--- a/data/etc/privapp-permissions-platform.xml
+++ b/data/etc/privapp-permissions-platform.xml
@@ -104,16 +104,6 @@ applications that come with the platform
<permission name="android.permission.WRITE_SECURE_SETTINGS"/>
</privapp-permissions>
- <privapp-permissions package="com.android.omadm.service">
- <permission name="android.permission.CHANGE_CONFIGURATION"/>
- <permission name="android.permission.CONNECTIVITY_INTERNAL"/>
- <permission name="android.permission.CONNECTIVITY_USE_RESTRICTED_NETWORKS"/>
- <permission name="android.permission.MODIFY_PHONE_STATE"/>
- <permission name="android.permission.READ_PRIVILEGED_PHONE_STATE"/>
- <permission name="android.permission.WRITE_APN_SETTINGS"/>
- <permission name="android.permission.WRITE_SECURE_SETTINGS"/>
- </privapp-permissions>
-
<privapp-permissions package="com.android.packageinstaller">
<permission name="android.permission.DELETE_PACKAGES"/>
<permission name="android.permission.INSTALL_PACKAGES"/>
diff --git a/graphics/java/android/graphics/ImageFormat.java b/graphics/java/android/graphics/ImageFormat.java
index 0787d8518fa5..62647741dcfa 100644
--- a/graphics/java/android/graphics/ImageFormat.java
+++ b/graphics/java/android/graphics/ImageFormat.java
@@ -716,6 +716,14 @@ public class ImageFormat {
public static final int PRIVATE = 0x22;
/**
+ * Compressed HEIC format.
+ *
+ * <p>This format defines the HEIC brand of High Efficiency Image File
+ * Format as described in ISO/IEC 23008-12.</p>
+ */
+ public static final int HEIC = 0x48454946;
+
+ /**
* Use this function to retrieve the number of bits per pixel of an
* ImageFormat.
*
@@ -796,6 +804,7 @@ public class ImageFormat {
case RAW_DEPTH:
case Y8:
case DEPTH_JPEG:
+ case HEIC:
return true;
}
diff --git a/graphics/java/android/graphics/Typeface.java b/graphics/java/android/graphics/Typeface.java
index bb04ff3cc9ff..7c9529b8ff71 100644
--- a/graphics/java/android/graphics/Typeface.java
+++ b/graphics/java/android/graphics/Typeface.java
@@ -134,7 +134,7 @@ public class Typeface {
/**
* @deprecated Use {@link android.graphics.fonts.FontFamily} instead.
*/
- @UnsupportedAppUsage
+ @UnsupportedAppUsage(trackingBug = 123768928)
@Deprecated
static final Map<String, android.graphics.FontFamily[]> sSystemFallbackMap =
Collections.emptyMap();
@@ -1003,7 +1003,7 @@ public class Typeface {
* @deprecated
*/
@Deprecated
- @UnsupportedAppUsage
+ @UnsupportedAppUsage(trackingBug = 123768928)
private static Typeface createFromFamilies(android.graphics.FontFamily[] families) {
long[] ptrArray = new long[families.length];
for (int i = 0; i < families.length; i++) {
@@ -1054,7 +1054,7 @@ public class Typeface {
*
* @deprecated Use {@link android.graphics.fonts.FontFamily} instead.
*/
- @UnsupportedAppUsage
+ @UnsupportedAppUsage(trackingBug = 123768928)
@Deprecated
private static Typeface createFromFamiliesWithDefault(android.graphics.FontFamily[] families,
String fallbackName, int weight, int italic) {
diff --git a/libs/androidfw/AssetManager2.cpp b/libs/androidfw/AssetManager2.cpp
index 20303eba6667..81afd937d85e 100644
--- a/libs/androidfw/AssetManager2.cpp
+++ b/libs/androidfw/AssetManager2.cpp
@@ -704,9 +704,29 @@ ApkAssetsCookie AssetManager2::ResolveReference(ApkAssetsCookie cookie, Res_valu
return cookie;
}
+const std::vector<uint32_t> AssetManager2::GetBagResIdStack(uint32_t resid) {
+ auto cached_iter = cached_bag_resid_stacks_.find(resid);
+ if (cached_iter != cached_bag_resid_stacks_.end()) {
+ return cached_iter->second;
+ } else {
+ auto found_resids = std::vector<uint32_t>();
+ GetBag(resid, found_resids);
+ // Cache style stacks if they are not already cached.
+ cached_bag_resid_stacks_[resid] = found_resids;
+ return found_resids;
+ }
+}
+
const ResolvedBag* AssetManager2::GetBag(uint32_t resid) {
auto found_resids = std::vector<uint32_t>();
- return GetBag(resid, found_resids);
+ auto bag = GetBag(resid, found_resids);
+
+ // Cache style stacks if they are not already cached.
+ auto cached_iter = cached_bag_resid_stacks_.find(resid);
+ if (cached_iter == cached_bag_resid_stacks_.end()) {
+ cached_bag_resid_stacks_[resid] = found_resids;
+ }
+ return bag;
}
const ResolvedBag* AssetManager2::GetBag(uint32_t resid, std::vector<uint32_t>& child_resids) {
diff --git a/libs/androidfw/include/androidfw/AssetManager2.h b/libs/androidfw/include/androidfw/AssetManager2.h
index f29769b834d1..d862182d8960 100644
--- a/libs/androidfw/include/androidfw/AssetManager2.h
+++ b/libs/androidfw/include/androidfw/AssetManager2.h
@@ -237,6 +237,8 @@ class AssetManager2 {
// resource has been resolved yet.
std::string GetLastResourceResolution() const;
+ const std::vector<uint32_t> GetBagResIdStack(uint32_t resid);
+
// Retrieves the best matching bag/map resource with ID `resid`.
// This method will resolve all parent references for this bag and merge keys with the child.
// To iterate over the keys, use the following idiom:
@@ -355,6 +357,10 @@ class AssetManager2 {
// which involves some calculation.
std::unordered_map<uint32_t, util::unique_cptr<ResolvedBag>> cached_bags_;
+ // Cached set of bag resid stacks for each bag. These are cached because they might be requested
+ // a number of times for each view during View inspection.
+ std::unordered_map<uint32_t, std::vector<uint32_t>> cached_bag_resid_stacks_;
+
// Whether or not to save resource resolution steps
bool resource_resolution_logging_enabled_ = false;
diff --git a/location/java/android/location/GnssMeasurement.java b/location/java/android/location/GnssMeasurement.java
index 602cc3e6d0fd..59eff6401deb 100644
--- a/location/java/android/location/GnssMeasurement.java
+++ b/location/java/android/location/GnssMeasurement.java
@@ -17,6 +17,7 @@
package android.location;
import android.annotation.IntDef;
+import android.annotation.NonNull;
import android.annotation.TestApi;
import android.os.Parcel;
import android.os.Parcelable;
@@ -49,6 +50,7 @@ public final class GnssMeasurement implements Parcelable {
private double mSnrInDb;
private double mAutomaticGainControlLevelInDb;
private int mCodeType;
+ private String mOtherCodeTypeName;
// The following enumerations must be in sync with the values declared in gps.h
@@ -209,8 +211,8 @@ public final class GnssMeasurement implements Parcelable {
*/
@IntDef(prefix = { "CODE_TYPE_" }, value = {
CODE_TYPE_UNKNOWN, CODE_TYPE_A, CODE_TYPE_B, CODE_TYPE_C, CODE_TYPE_I, CODE_TYPE_L,
- CODE_TYPE_M, CODE_TYPE_P, CODE_TYPE_Q, CODE_TYPE_S, CODE_TYPE_W, CODE_TYPE_X,
- CODE_TYPE_Y, CODE_TYPE_Z, CODE_TYPE_CODELESS
+ CODE_TYPE_M, CODE_TYPE_N, CODE_TYPE_P, CODE_TYPE_Q, CODE_TYPE_S, CODE_TYPE_W,
+ CODE_TYPE_X, CODE_TYPE_Y, CODE_TYPE_Z, CODE_TYPE_OTHER
})
@Retention(RetentionPolicy.SOURCE)
public @interface CodeType {}
@@ -299,7 +301,16 @@ public final class GnssMeasurement implements Parcelable {
/**
* The GNSS Measurement's code type is one of the following: GPS L1 codeless, GPS L2 codeless.
*/
- public static final int CODE_TYPE_CODELESS = 13;
+ public static final int CODE_TYPE_N = 13;
+
+ /**
+ * Other code type that does not belong to any of the above code types.
+ *
+ * This code type is used in the case that the code type being tracked in this measurement, as
+ * classified by RINEX standards, does not fit into one of the existing enumerated values. When
+ * this code type is set, the field otherCodeTypeName must specify the new code type.
+ */
+ public static final int CODE_TYPE_OTHER = 255;
/**
* All the 'Accumulated Delta Range' flags.
@@ -349,6 +360,7 @@ public final class GnssMeasurement implements Parcelable {
mSnrInDb = measurement.mSnrInDb;
mAutomaticGainControlLevelInDb = measurement.mAutomaticGainControlLevelInDb;
mCodeType = measurement.mCodeType;
+ mOtherCodeTypeName = measurement.mOtherCodeTypeName;
}
/**
@@ -1175,8 +1187,8 @@ public final class GnssMeasurement implements Parcelable {
/**
* Gets the GNSS measurement's code type.
*
- * <p>Similar to the Attribute field described in Rinex 3.03, e.g., in Tables 4-10, and Table
- * A2 at the Rinex 3.03 Update 1 Document.
+ * <p>Similar to the Attribute field described in RINEX 3.03, e.g., in Tables 4-10, and Table
+ * A2 at the RINEX 3.03 Update 1 Document.
*/
@CodeType
public int getCodeType() {
@@ -1206,6 +1218,29 @@ public final class GnssMeasurement implements Parcelable {
}
/**
+ * Gets the GNSS measurement's code type name when the code type is {@link #CODE_TYPE_OTHER}.
+ *
+ * <p>This is used to specify the observation descriptor defined in GNSS Observation Data File
+ * Header Section Description in the RINEX standard (Version 3.XX), in cases where the code type
+ * does not align with an existing Android enumerated value. For example, if a code type "G" is
+ * added, this string shall be set to "G".
+ */
+ @NonNull
+ public String getOtherCodeTypeName() {
+ return mOtherCodeTypeName;
+ }
+
+ /**
+ * Sets the GNSS measurement's code type name when the code type is {@link #CODE_TYPE_OTHER}.
+ *
+ * @hide
+ */
+ @TestApi
+ public void setOtherCodeTypeName(@NonNull String otherCodeTypeName) {
+ mOtherCodeTypeName = otherCodeTypeName;
+ }
+
+ /**
* Gets a string representation of the 'code type'.
*
* <p>For internal and logging use only.
@@ -1226,6 +1261,8 @@ public final class GnssMeasurement implements Parcelable {
return "CODE_TYPE_L";
case CODE_TYPE_M:
return "CODE_TYPE_M";
+ case CODE_TYPE_N:
+ return "CODE_TYPE_N";
case CODE_TYPE_P:
return "CODE_TYPE_P";
case CODE_TYPE_Q:
@@ -1240,8 +1277,8 @@ public final class GnssMeasurement implements Parcelable {
return "CODE_TYPE_Y";
case CODE_TYPE_Z:
return "CODE_TYPE_Z";
- case CODE_TYPE_CODELESS:
- return "CODE_TYPE_CODELESS";
+ case CODE_TYPE_OTHER:
+ return "CODE_TYPE_OTHER";
default:
return "<Invalid: " + mCodeType + ">";
}
@@ -1273,6 +1310,7 @@ public final class GnssMeasurement implements Parcelable {
gnssMeasurement.mSnrInDb = parcel.readDouble();
gnssMeasurement.mAutomaticGainControlLevelInDb = parcel.readDouble();
gnssMeasurement.mCodeType = parcel.readInt();
+ gnssMeasurement.mOtherCodeTypeName = parcel.readString();
return gnssMeasurement;
}
@@ -1306,6 +1344,7 @@ public final class GnssMeasurement implements Parcelable {
parcel.writeDouble(mSnrInDb);
parcel.writeDouble(mAutomaticGainControlLevelInDb);
parcel.writeInt(mCodeType);
+ parcel.writeString(mOtherCodeTypeName);
}
@Override
@@ -1384,6 +1423,9 @@ public final class GnssMeasurement implements Parcelable {
format,
"CodeType",
hasCodeType() ? getCodeTypeString() : null));
+ builder.append(String.format(
+ format,
+ "OtherCodeTypeName", mOtherCodeTypeName));
return builder.toString();
}
@@ -1409,6 +1451,7 @@ public final class GnssMeasurement implements Parcelable {
resetSnrInDb();
resetAutomaticGainControlLevel();
resetCodeType();
+ setOtherCodeTypeName("");
}
private void setFlag(int flag) {
diff --git a/media/java/android/media/Image.java b/media/java/android/media/Image.java
index 26b9b8cf85a7..70a343f4de01 100644
--- a/media/java/android/media/Image.java
+++ b/media/java/android/media/Image.java
@@ -155,6 +155,13 @@ public abstract class Image implements AutoCloseable {
* UnSupportedOperationException being thrown.
* </td>
* </tr>
+ * <tr>
+ * <td>{@link android.graphics.ImageFormat#HEIC HEIC}</td>
+ * <td>1</td>
+ * <td>Compressed data, so row and pixel strides are 0. To uncompress, use
+ * {@link android.graphics.BitmapFactory#decodeByteArray BitmapFactory#decodeByteArray}.
+ * </td>
+ * </tr>
* </table>
*
* @see android.graphics.ImageFormat
diff --git a/media/java/android/media/ImageReader.java b/media/java/android/media/ImageReader.java
index 60ef1d93191a..6116429ae561 100644
--- a/media/java/android/media/ImageReader.java
+++ b/media/java/android/media/ImageReader.java
@@ -821,6 +821,7 @@ public class ImageReader implements AutoCloseable {
case ImageFormat.DEPTH_POINT_CLOUD:
case ImageFormat.RAW_PRIVATE:
case ImageFormat.DEPTH_JPEG:
+ case ImageFormat.HEIC:
width = ImageReader.this.getWidth();
break;
default:
@@ -838,6 +839,7 @@ public class ImageReader implements AutoCloseable {
case ImageFormat.DEPTH_POINT_CLOUD:
case ImageFormat.RAW_PRIVATE:
case ImageFormat.DEPTH_JPEG:
+ case ImageFormat.HEIC:
height = ImageReader.this.getHeight();
break;
default:
diff --git a/media/java/android/media/ImageUtils.java b/media/java/android/media/ImageUtils.java
index b77a884d3412..d8a0bb334c53 100644
--- a/media/java/android/media/ImageUtils.java
+++ b/media/java/android/media/ImageUtils.java
@@ -36,8 +36,8 @@ class ImageUtils {
* {@link android.graphics.PixelFormat PixelFormat} are supported by
* ImageReader. When reading RGB data from a surface, the formats defined in
* {@link android.graphics.PixelFormat PixelFormat} can be used; when
- * reading YUV, JPEG or raw sensor data (for example, from the camera or video
- * decoder), formats from {@link android.graphics.ImageFormat ImageFormat}
+ * reading YUV, JPEG, HEIC or raw sensor data (for example, from the camera
+ * or video decoder), formats from {@link android.graphics.ImageFormat ImageFormat}
* are used.
*/
public static int getNumPlanesForFormat(int format) {
@@ -64,6 +64,7 @@ class ImageUtils {
case ImageFormat.DEPTH_POINT_CLOUD:
case ImageFormat.RAW_DEPTH:
case ImageFormat.DEPTH_JPEG:
+ case ImageFormat.HEIC:
return 1;
case ImageFormat.PRIVATE:
return 0;
@@ -194,6 +195,7 @@ class ImageUtils {
case ImageFormat.JPEG:
case ImageFormat.DEPTH_POINT_CLOUD:
case ImageFormat.DEPTH_JPEG:
+ case ImageFormat.HEIC:
estimatedBytePerPixel = 0.3;
break;
case ImageFormat.Y8:
@@ -262,6 +264,7 @@ class ImageUtils {
case ImageFormat.RAW10:
case ImageFormat.RAW12:
case ImageFormat.RAW_DEPTH:
+ case ImageFormat.HEIC:
return new Size(image.getWidth(), image.getHeight());
case ImageFormat.PRIVATE:
return new Size(0, 0);
diff --git a/media/java/android/media/audiopolicy/AudioMix.java b/media/java/android/media/audiopolicy/AudioMix.java
index 1c6210e0c060..761b62588e5a 100644
--- a/media/java/android/media/audiopolicy/AudioMix.java
+++ b/media/java/android/media/audiopolicy/AudioMix.java
@@ -353,11 +353,6 @@ public class AudioMix {
// no route flags set, use default as described in Builder.setRouteFlags(int)
mRouteFlags = ROUTE_FLAG_LOOP_BACK;
}
- // can't do loop back AND render at same time in this implementation
- if (mRouteFlags == (ROUTE_FLAG_RENDER | ROUTE_FLAG_LOOP_BACK)) {
- throw new IllegalArgumentException("Unsupported route behavior combination 0x" +
- Integer.toHexString(mRouteFlags));
- }
if (mFormat == null) {
// FIXME Can we eliminate this? Will AudioMix work with an unspecified sample rate?
int rate = AudioSystem.getPrimaryOutputSamplingRate();
@@ -377,11 +372,11 @@ public class AudioMix {
throw new IllegalArgumentException("Unsupported device on non-playback mix");
}
} else {
- if ((mRouteFlags & ROUTE_FLAG_RENDER) == ROUTE_FLAG_RENDER) {
+ if ((mRouteFlags & ROUTE_FLAG_SUPPORTED) == ROUTE_FLAG_RENDER) {
throw new IllegalArgumentException(
"Can't have flag ROUTE_FLAG_RENDER without an audio device");
}
- if ((mRouteFlags & ROUTE_FLAG_SUPPORTED) == ROUTE_FLAG_LOOP_BACK) {
+ if ((mRouteFlags & ROUTE_FLAG_LOOP_BACK) == ROUTE_FLAG_LOOP_BACK) {
if (mRule.getTargetMixType() == MIX_TYPE_PLAYERS) {
mDeviceSystemType = AudioSystem.DEVICE_OUT_REMOTE_SUBMIX;
} else if (mRule.getTargetMixType() == MIX_TYPE_RECORDERS) {
diff --git a/media/jni/android_media_MediaCodec.cpp b/media/jni/android_media_MediaCodec.cpp
index 406f9dd94bb4..f07f1e8fb62b 100644
--- a/media/jni/android_media_MediaCodec.cpp
+++ b/media/jni/android_media_MediaCodec.cpp
@@ -153,8 +153,12 @@ JMediaCodec::JMediaCodec(
if (nameIsType) {
mCodec = MediaCodec::CreateByType(mLooper, name, encoder, &mInitStatus);
+ if (mCodec == nullptr || mCodec->getName(&mNameAtCreation) != OK) {
+ mNameAtCreation = "(null)";
+ }
} else {
mCodec = MediaCodec::CreateByComponentName(mLooper, name, &mInitStatus);
+ mNameAtCreation = name;
}
CHECK((mCodec != NULL) != (mInitStatus != OK));
}
@@ -699,9 +703,8 @@ status_t JMediaCodec::getCodecInfo(JNIEnv *env, jobject *codecInfoObject) const
return err;
}
- // TODO: get alias
ScopedLocalRef<jstring> nameObject(env,
- env->NewStringUTF(codecInfo->getCodecName()));
+ env->NewStringUTF(mNameAtCreation.c_str()));
ScopedLocalRef<jstring> canonicalNameObject(env,
env->NewStringUTF(codecInfo->getCodecName()));
diff --git a/media/jni/android_media_MediaCodec.h b/media/jni/android_media_MediaCodec.h
index 0a53f1a0e268..de08550fa3db 100644
--- a/media/jni/android_media_MediaCodec.h
+++ b/media/jni/android_media_MediaCodec.h
@@ -155,6 +155,7 @@ private:
sp<ALooper> mLooper;
sp<MediaCodec> mCodec;
+ AString mNameAtCreation;
sp<AMessage> mCallbackNotification;
sp<AMessage> mOnFrameRenderedNotification;
diff --git a/media/jni/android_media_MediaCodecList.cpp b/media/jni/android_media_MediaCodecList.cpp
index cf1494296756..6b8f7457eab9 100644
--- a/media/jni/android_media_MediaCodecList.cpp
+++ b/media/jni/android_media_MediaCodecList.cpp
@@ -24,6 +24,10 @@
#include <media/IMediaCodecList.h>
#include <media/MediaCodecInfo.h>
+#include <utils/Vector.h>
+
+#include <vector>
+
#include "android_runtime/AndroidRuntime.h"
#include "jni.h"
#include <nativehelper/JNIHelp.h>
@@ -31,25 +35,91 @@
using namespace android;
-static sp<IMediaCodecList> getCodecList(JNIEnv *env) {
- sp<IMediaCodecList> mcl = MediaCodecList::getInstance();
- if (mcl == NULL) {
- // This should never happen unless something is really wrong
- jniThrowException(
- env, "java/lang/RuntimeException", "cannot get MediaCodecList");
+/**
+ * This object unwraps codec aliases into individual codec infos as the Java interface handles
+ * aliases in this way.
+ */
+class JavaMediaCodecListWrapper {
+public:
+ struct Info {
+ sp<MediaCodecInfo> info;
+ AString alias;
+ };
+
+ const Info getCodecInfo(size_t index) const {
+ if (index < mInfoList.size()) {
+ return mInfoList[index];
+ }
+ // return
+ return Info { nullptr /* info */, "(none)" /* alias */ };
+ }
+
+ size_t countCodecs() const {
+ return mInfoList.size();
}
- return mcl;
+
+ sp<IMediaCodecList> getCodecList() const {
+ return mCodecList;
+ }
+
+ size_t findCodecByName(AString name) const {
+ auto it = mInfoIndex.find(name);
+ return it == mInfoIndex.end() ? -ENOENT : it->second;
+ }
+
+ JavaMediaCodecListWrapper(sp<IMediaCodecList> mcl)
+ : mCodecList(mcl) {
+ size_t numCodecs = mcl->countCodecs();
+ for (size_t ix = 0; ix < numCodecs; ++ix) {
+ sp<MediaCodecInfo> info = mcl->getCodecInfo(ix);
+ Vector<AString> namesAndAliases;
+ info->getAliases(&namesAndAliases);
+ namesAndAliases.insertAt(0);
+ namesAndAliases.editItemAt(0) = info->getCodecName();
+ for (const AString &nameOrAlias : namesAndAliases) {
+ if (mInfoIndex.count(nameOrAlias) > 0) {
+ // skip duplicate names or aliases
+ continue;
+ }
+ mInfoIndex.emplace(nameOrAlias, mInfoList.size());
+ mInfoList.emplace_back(Info { info, nameOrAlias });
+ }
+ }
+ }
+
+private:
+ sp<IMediaCodecList> mCodecList;
+ std::vector<Info> mInfoList;
+ std::map<AString, size_t> mInfoIndex;
+};
+
+static std::mutex sMutex;
+static std::unique_ptr<JavaMediaCodecListWrapper> sListWrapper;
+
+static const JavaMediaCodecListWrapper *getCodecList(JNIEnv *env) {
+ std::lock_guard<std::mutex> lock(sMutex);
+ if (sListWrapper == nullptr) {
+ sp<IMediaCodecList> mcl = MediaCodecList::getInstance();
+ if (mcl == NULL) {
+ // This should never happen unless something is really wrong
+ jniThrowException(
+ env, "java/lang/RuntimeException", "cannot get MediaCodecList");
+ }
+
+ sListWrapper.reset(new JavaMediaCodecListWrapper(mcl));
+ }
+ return sListWrapper.get();
}
-static sp<MediaCodecInfo> getCodecInfo(JNIEnv *env, jint index) {
- sp<IMediaCodecList> mcl = getCodecList(env);
- if (mcl == NULL) {
+static JavaMediaCodecListWrapper::Info getCodecInfo(JNIEnv *env, jint index) {
+ const JavaMediaCodecListWrapper *mcl = getCodecList(env);
+ if (mcl == nullptr) {
// Runtime exception already pending.
- return NULL;
+ return JavaMediaCodecListWrapper::Info { nullptr /* info */, "(none)" /* alias */ };
}
- sp<MediaCodecInfo> info = mcl->getCodecInfo(index);
- if (info == NULL) {
+ JavaMediaCodecListWrapper::Info info = mcl->getCodecInfo(index);
+ if (info.info == NULL) {
jniThrowException(env, "java/lang/IllegalArgumentException", NULL);
}
@@ -58,36 +128,36 @@ static sp<MediaCodecInfo> getCodecInfo(JNIEnv *env, jint index) {
static jint android_media_MediaCodecList_getCodecCount(
JNIEnv *env, jobject /* thiz */) {
- sp<IMediaCodecList> mcl = getCodecList(env);
+ const JavaMediaCodecListWrapper *mcl = getCodecList(env);
if (mcl == NULL) {
// Runtime exception already pending.
return 0;
}
+
return mcl->countCodecs();
}
static jstring android_media_MediaCodecList_getCodecName(
JNIEnv *env, jobject /* thiz */, jint index) {
- sp<MediaCodecInfo> info = getCodecInfo(env, index);
- if (info == NULL) {
+ JavaMediaCodecListWrapper::Info info = getCodecInfo(env, index);
+ if (info.info == NULL) {
// Runtime exception already pending.
return NULL;
}
- // TODO: support aliases
- const char *name = info->getCodecName();
+ const char *name = info.alias.c_str();
return env->NewStringUTF(name);
}
static jstring android_media_MediaCodecList_getCanonicalName(
JNIEnv *env, jobject /* thiz */, jint index) {
- sp<MediaCodecInfo> info = getCodecInfo(env, index);
- if (info == NULL) {
+ JavaMediaCodecListWrapper::Info info = getCodecInfo(env, index);
+ if (info.info == NULL) {
// Runtime exception already pending.
return NULL;
}
- const char *name = info->getCodecName();
+ const char *name = info.info->getCodecName();
return env->NewStringUTF(name);
}
@@ -104,7 +174,7 @@ static jint android_media_MediaCodecList_findCodecByName(
return -ENOENT;
}
- sp<IMediaCodecList> mcl = getCodecList(env);
+ const JavaMediaCodecListWrapper *mcl = getCodecList(env);
if (mcl == NULL) {
// Runtime exception already pending.
env->ReleaseStringUTFChars(name, nameStr);
@@ -118,25 +188,25 @@ static jint android_media_MediaCodecList_findCodecByName(
static jboolean android_media_MediaCodecList_getAttributes(
JNIEnv *env, jobject /* thiz */, jint index) {
- sp<MediaCodecInfo> info = getCodecInfo(env, index);
- if (info == NULL) {
+ JavaMediaCodecListWrapper::Info info = getCodecInfo(env, index);
+ if (info.info == NULL) {
// Runtime exception already pending.
return 0;
}
- return info->getAttributes();
+ return info.info->getAttributes();
}
static jarray android_media_MediaCodecList_getSupportedTypes(
JNIEnv *env, jobject /* thiz */, jint index) {
- sp<MediaCodecInfo> info = getCodecInfo(env, index);
- if (info == NULL) {
+ JavaMediaCodecListWrapper::Info info = getCodecInfo(env, index);
+ if (info.info == NULL) {
// Runtime exception already pending.
return NULL;
}
Vector<AString> types;
- info->getSupportedMediaTypes(&types);
+ info.info->getSupportedMediaTypes(&types);
jclass clazz = env->FindClass("java/lang/String");
CHECK(clazz != NULL);
@@ -160,8 +230,8 @@ static jobject android_media_MediaCodecList_getCodecCapabilities(
return NULL;
}
- sp<MediaCodecInfo> info = getCodecInfo(env, index);
- if (info == NULL) {
+ JavaMediaCodecListWrapper::Info info = getCodecInfo(env, index);
+ if (info.info == NULL) {
// Runtime exception already pending.
return NULL;
}
@@ -181,7 +251,7 @@ static jobject android_media_MediaCodecList_getCodecCapabilities(
// TODO query default-format also from codec/codec list
const sp<MediaCodecInfo::Capabilities> &capabilities =
- info->getCapabilitiesFor(typeStr);
+ info.info->getCapabilitiesFor(typeStr);
env->ReleaseStringUTFChars(type, typeStr);
typeStr = NULL;
if (capabilities == NULL) {
@@ -192,7 +262,7 @@ static jobject android_media_MediaCodecList_getCodecCapabilities(
capabilities->getSupportedColorFormats(&colorFormats);
capabilities->getSupportedProfileLevels(&profileLevels);
sp<AMessage> details = capabilities->getDetails();
- bool isEncoder = info->isEncoder();
+ bool isEncoder = info.info->isEncoder();
jobject defaultFormatObj = NULL;
if (ConvertMessageToMap(env, defaultFormat, &defaultFormatObj)) {
@@ -267,13 +337,13 @@ static jobject android_media_MediaCodecList_getCodecCapabilities(
}
static jobject android_media_MediaCodecList_getGlobalSettings(JNIEnv *env, jobject /* thiz */) {
- sp<IMediaCodecList> mcl = getCodecList(env);
+ const JavaMediaCodecListWrapper *mcl = getCodecList(env);
if (mcl == NULL) {
// Runtime exception already pending.
return NULL;
}
- const sp<AMessage> settings = mcl->getGlobalSettings();
+ const sp<AMessage> settings = mcl->getCodecList()->getGlobalSettings();
if (settings == NULL) {
jniThrowException(env, "java/lang/RuntimeException", "cannot get global settings");
return NULL;
diff --git a/media/jni/android_media_Utils.cpp b/media/jni/android_media_Utils.cpp
index 458d8471dafd..01baadb2f024 100644
--- a/media/jni/android_media_Utils.cpp
+++ b/media/jni/android_media_Utils.cpp
@@ -29,6 +29,9 @@
#define ALIGN(x, mask) ( ((x) + (mask) - 1) & ~((mask) - 1) )
+// Must be in sync with the value in HeicCompositeStream.cpp
+#define CAMERA3_HEIC_BLOB_ID 0x00FE
+
namespace android {
AssetStream::AssetStream(SkStream* stream)
@@ -609,34 +612,35 @@ bool isPossiblyYUV(PixelFormat format) {
}
}
-uint32_t Image_getJpegSize(LockedImage* buffer, bool usingRGBAOverride) {
+uint32_t Image_getBlobSize(LockedImage* buffer, bool usingRGBAOverride) {
ALOGV("%s", __FUNCTION__);
LOG_ALWAYS_FATAL_IF(buffer == NULL, "Input buffer is NULL!!!");
uint32_t size = 0;
uint32_t width = buffer->width;
- uint8_t* jpegBuffer = buffer->data;
+ uint8_t* blobBuffer = buffer->data;
if (usingRGBAOverride) {
width = (buffer->width + buffer->stride * (buffer->height - 1)) * 4;
}
- // First check for JPEG transport header at the end of the buffer
- uint8_t* header = jpegBuffer + (width - sizeof(struct camera3_jpeg_blob));
+ // First check for BLOB transport header at the end of the buffer
+ uint8_t* header = blobBuffer + (width - sizeof(struct camera3_jpeg_blob));
struct camera3_jpeg_blob *blob = (struct camera3_jpeg_blob*)(header);
- if (blob->jpeg_blob_id == CAMERA3_JPEG_BLOB_ID) {
+ if (blob->jpeg_blob_id == CAMERA3_JPEG_BLOB_ID ||
+ blob->jpeg_blob_id == CAMERA3_HEIC_BLOB_ID) {
size = blob->jpeg_size;
- ALOGV("%s: Jpeg size = %d", __FUNCTION__, size);
+ ALOGV("%s: Jpeg/Heic size = %d", __FUNCTION__, size);
}
// failed to find size, default to whole buffer
if (size == 0) {
/*
- * This is a problem because not including the JPEG header
- * means that in certain rare situations a regular JPEG blob
+ * This is a problem because not including the JPEG/BLOB header
+ * means that in certain rare situations a regular JPEG/HEIC blob
* will be mis-identified as having a header, in which case
* we will get a garbage size value.
*/
- ALOGW("%s: No JPEG header detected, defaulting to size=width=%d",
+ ALOGW("%s: No JPEG/HEIC header detected, defaulting to size=width=%d",
__FUNCTION__, width);
size = width;
}
@@ -760,7 +764,7 @@ status_t getLockedImageInfo(LockedImage* buffer, int idx,
pData = buffer->data;
- dataSize = Image_getJpegSize(buffer, usingRGBAOverride);
+ dataSize = Image_getBlobSize(buffer, usingRGBAOverride);
pStride = 0;
rStride = 0;
break;
diff --git a/media/jni/android_media_Utils.h b/media/jni/android_media_Utils.h
index 821c6b25c333..19c1b88f78e8 100644
--- a/media/jni/android_media_Utils.h
+++ b/media/jni/android_media_Utils.h
@@ -119,7 +119,7 @@ bool usingRGBAToJpegOverride(int32_t imageFormat, int32_t containerFormat);
int32_t applyFormatOverrides(int32_t imageFormat, int32_t containerFormat);
-uint32_t Image_getJpegSize(LockedImage* buffer, bool usingRGBAOverride);
+uint32_t Image_getBlobSize(LockedImage* buffer, bool usingRGBAOverride);
bool isFormatOpaque(int format);
diff --git a/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java b/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java
index dbffa6d6bcf2..0d6d080b6dc2 100644
--- a/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java
+++ b/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java
@@ -61,6 +61,7 @@ import android.net.util.SharedLog;
import android.net.util.Stopwatch;
import android.net.wifi.WifiInfo;
import android.net.wifi.WifiManager;
+import android.os.Bundle;
import android.os.Message;
import android.os.RemoteException;
import android.os.SystemClock;
@@ -674,11 +675,11 @@ public class NetworkMonitor extends StateMachine {
public boolean processMessage(Message message) {
switch (message.what) {
case CMD_LAUNCH_CAPTIVE_PORTAL_APP:
- final Intent intent = new Intent(
- ConnectivityManager.ACTION_CAPTIVE_PORTAL_SIGN_IN);
+ final Bundle appExtras = new Bundle();
// OneAddressPerFamilyNetwork is not parcelable across processes.
- intent.putExtra(ConnectivityManager.EXTRA_NETWORK, new Network(mNetwork));
- intent.putExtra(ConnectivityManager.EXTRA_CAPTIVE_PORTAL,
+ appExtras.putParcelable(
+ ConnectivityManager.EXTRA_NETWORK, new Network(mNetwork));
+ appExtras.putParcelable(ConnectivityManager.EXTRA_CAPTIVE_PORTAL,
new CaptivePortal(new ICaptivePortal.Stub() {
@Override
public void appResponse(int response) {
@@ -700,16 +701,14 @@ public class NetworkMonitor extends StateMachine {
}
}));
final CaptivePortalProbeResult probeRes = mLastPortalProbeResult;
- intent.putExtra(EXTRA_CAPTIVE_PORTAL_URL, probeRes.detectUrl);
+ appExtras.putString(EXTRA_CAPTIVE_PORTAL_URL, probeRes.detectUrl);
if (probeRes.probeSpec != null) {
final String encodedSpec = probeRes.probeSpec.getEncodedSpec();
- intent.putExtra(EXTRA_CAPTIVE_PORTAL_PROBE_SPEC, encodedSpec);
+ appExtras.putString(EXTRA_CAPTIVE_PORTAL_PROBE_SPEC, encodedSpec);
}
- intent.putExtra(ConnectivityManager.EXTRA_CAPTIVE_PORTAL_USER_AGENT,
+ appExtras.putString(ConnectivityManager.EXTRA_CAPTIVE_PORTAL_USER_AGENT,
mCaptivePortalUserAgent);
- intent.setFlags(
- Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT | Intent.FLAG_ACTIVITY_NEW_TASK);
- mContext.startActivityAsUser(intent, UserHandle.CURRENT);
+ mCm.startCaptivePortalApp(appExtras);
return HANDLED;
default:
return NOT_HANDLED;
diff --git a/packages/PrintSpooler/AndroidManifest.xml b/packages/PrintSpooler/AndroidManifest.xml
index 478ee54b40e5..cd6abb267e44 100644
--- a/packages/PrintSpooler/AndroidManifest.xml
+++ b/packages/PrintSpooler/AndroidManifest.xml
@@ -37,16 +37,8 @@
<uses-permission android:name="android.permission.READ_PRINT_SERVICES" />
<uses-permission android:name="android.permission.READ_PRINT_SERVICE_RECOMMENDATIONS" />
- <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"
- android:dataSentOffDevice="no"
- android:dataSharedWithThirdParty="no"
- android:dataUsedForMonetization="no"
- android:dataRetentionTime="unlimited"/>
- <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"
- android:dataSentOffDevice="no"
- android:dataSharedWithThirdParty="no"
- android:dataUsedForMonetization="no"
- android:dataRetentionTime="unlimited"/>
+ <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
+ <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<application
android:allowClearUserData="true"
diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProtoDumpUtil.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProtoDumpUtil.java
index fad93cbf83da..6152b8cbd562 100644
--- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProtoDumpUtil.java
+++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProtoDumpUtil.java
@@ -457,6 +457,9 @@ class SettingsProtoDumpUtil {
dumpSetting(s, p,
Settings.Global.DEBUG_VIEW_ATTRIBUTES,
GlobalSettingsProto.Debug.VIEW_ATTRIBUTES);
+ dumpSetting(s, p,
+ Settings.Global.DEBUG_VIEW_ATTRIBUTES_APPLICATION_PACKAGE,
+ GlobalSettingsProto.Debug.VIEW_ATTRIBUTES_APPLICATION_PACKAGE);
p.end(debugToken);
final long defaultToken = p.start(GlobalSettingsProto.DEFAULT);
diff --git a/packages/SystemUI/AndroidManifest.xml b/packages/SystemUI/AndroidManifest.xml
index 866b46f732d8..3778a9c1cf83 100644
--- a/packages/SystemUI/AndroidManifest.xml
+++ b/packages/SystemUI/AndroidManifest.xml
@@ -22,11 +22,6 @@
android:sharedUserId="android.uid.systemui"
coreApp="true">
- <!-- Using OpenGL ES 2.0 -->
- <uses-feature
- android:glEsVersion="0x00020000"
- android:required="true" />
-
<!-- SysUI must be the one to define this permission; its name is
referenced by the core OS. -->
<permission android:name="android.permission.systemui.IDENTITY"
diff --git a/packages/SystemUI/res/raw/image_wallpaper_fragment_shader.glsl b/packages/SystemUI/res/raw/image_wallpaper_fragment_shader.glsl
deleted file mode 100644
index 11d73a93ad04..000000000000
--- a/packages/SystemUI/res/raw/image_wallpaper_fragment_shader.glsl
+++ /dev/null
@@ -1,33 +0,0 @@
-precision mediump float;
-
-uniform sampler2D uTexture;
-uniform float uCenterReveal;
-uniform float uReveal;
-uniform float uAod2Opacity;
-uniform int uAodMode;
-varying vec2 vTextureCoordinates;
-
-vec3 luminosity(vec3 color) {
- float lum = 0.2126 * color.r + 0.7152 * color.g + 0.0722 * color.b;
- return vec3(lum);
-}
-
-vec4 transform(vec3 diffuse) {
- // TODO: Add well comments here, tracking on b/123615467.
- vec3 lum = luminosity(diffuse);
- diffuse = mix(diffuse, lum, smoothstep(0., uCenterReveal, uReveal));
- float val = mix(uReveal, uCenterReveal, step(uCenterReveal, uReveal));
- diffuse = smoothstep(val, 1.0, diffuse);
- diffuse *= uAod2Opacity * (1. - smoothstep(uCenterReveal, 1., uReveal));
- return vec4(diffuse.r, diffuse.g, diffuse.b, 1.);
-}
-
-void main() {
- vec4 fragColor = texture2D(uTexture, vTextureCoordinates);
- // TODO: Remove the branch logic here, tracking on b/123615467.
- if (uAodMode != 0) {
- gl_FragColor = transform(fragColor.rgb);
- } else {
- gl_FragColor = fragColor;
- }
-} \ No newline at end of file
diff --git a/packages/SystemUI/res/raw/image_wallpaper_vertex_shader.glsl b/packages/SystemUI/res/raw/image_wallpaper_vertex_shader.glsl
deleted file mode 100644
index 4393e2bb0ebf..000000000000
--- a/packages/SystemUI/res/raw/image_wallpaper_vertex_shader.glsl
+++ /dev/null
@@ -1,8 +0,0 @@
-attribute vec4 aPosition;
-attribute vec2 aTextureCoordinates;
-varying vec2 vTextureCoordinates;
-
-void main() {
- vTextureCoordinates = aTextureCoordinates;
- gl_Position = aPosition;
-} \ No newline at end of file
diff --git a/packages/SystemUI/src/com/android/systemui/Dependency.java b/packages/SystemUI/src/com/android/systemui/Dependency.java
index fece94e69a3d..c3f61eee4930 100644
--- a/packages/SystemUI/src/com/android/systemui/Dependency.java
+++ b/packages/SystemUI/src/com/android/systemui/Dependency.java
@@ -18,6 +18,7 @@ import android.annotation.Nullable;
import android.content.Context;
import android.content.res.Configuration;
import android.hardware.SensorPrivacyManager;
+import android.hardware.display.NightDisplayListener;
import android.os.Handler;
import android.os.Looper;
import android.util.ArrayMap;
@@ -25,7 +26,6 @@ import android.util.DisplayMetrics;
import android.view.IWindowManager;
import com.android.internal.annotations.VisibleForTesting;
-import com.android.internal.app.ColorDisplayController;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.statusbar.IStatusBarService;
import com.android.internal.util.Preconditions;
@@ -206,7 +206,7 @@ public class Dependency extends SystemUI {
@Inject Lazy<UserInfoController> mUserInfoController;
@Inject Lazy<KeyguardMonitor> mKeyguardMonitor;
@Inject Lazy<BatteryController> mBatteryController;
- @Inject Lazy<ColorDisplayController> mColorDisplayController;
+ @Inject Lazy<NightDisplayListener> mNightDisplayListener;
@Inject Lazy<ManagedProfileController> mManagedProfileController;
@Inject Lazy<NextAlarmController> mNextAlarmController;
@Inject Lazy<DataSaverController> mDataSaverController;
@@ -330,7 +330,7 @@ public class Dependency extends SystemUI {
mProviders.put(BatteryController.class, mBatteryController::get);
- mProviders.put(ColorDisplayController.class, mColorDisplayController::get);
+ mProviders.put(NightDisplayListener.class, mNightDisplayListener::get);
mProviders.put(ManagedProfileController.class, mManagedProfileController::get);
diff --git a/packages/SystemUI/src/com/android/systemui/DependencyProvider.java b/packages/SystemUI/src/com/android/systemui/DependencyProvider.java
index 88e32cbeaa29..a517d7ce8e0e 100644
--- a/packages/SystemUI/src/com/android/systemui/DependencyProvider.java
+++ b/packages/SystemUI/src/com/android/systemui/DependencyProvider.java
@@ -24,6 +24,7 @@ import static com.android.systemui.Dependency.TIME_TICK_HANDLER_NAME;
import android.annotation.Nullable;
import android.content.Context;
import android.hardware.SensorPrivacyManager;
+import android.hardware.display.NightDisplayListener;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.Looper;
@@ -34,7 +35,6 @@ import android.util.DisplayMetrics;
import android.view.IWindowManager;
import android.view.WindowManagerGlobal;
-import com.android.internal.app.ColorDisplayController;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.statusbar.IStatusBarService;
import com.android.settingslib.bluetooth.LocalBluetoothManager;
@@ -152,8 +152,8 @@ public class DependencyProvider {
@Singleton
@Provides
- public ColorDisplayController provideColorDisplayController(Context context) {
- return new ColorDisplayController(context);
+ public NightDisplayListener provideNightDisplayListener(Context context) {
+ return new NightDisplayListener(context);
}
@Singleton
diff --git a/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java b/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java
index 50409421a68b..2aecc24e83c0 100644
--- a/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java
+++ b/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java
@@ -19,11 +19,8 @@ package com.android.systemui;
import static android.view.Display.DEFAULT_DISPLAY;
import android.app.WallpaperManager;
-import android.content.BroadcastReceiver;
import android.content.ComponentCallbacks2;
import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.RecordingCanvas;
@@ -31,9 +28,7 @@ import android.graphics.Rect;
import android.graphics.RectF;
import android.graphics.Region.Op;
import android.hardware.display.DisplayManager;
-import android.opengl.GLSurfaceView;
import android.os.AsyncTask;
-import android.os.Build;
import android.os.Handler;
import android.os.Trace;
import android.service.wallpaper.WallpaperService;
@@ -44,7 +39,6 @@ import android.view.Surface;
import android.view.SurfaceHolder;
import com.android.internal.annotations.VisibleForTesting;
-import com.android.systemui.glwallpaper.ImageWallpaperRenderer;
import java.io.FileDescriptor;
import java.io.IOException;
@@ -57,17 +51,12 @@ import java.io.PrintWriter;
public class ImageWallpaper extends WallpaperService {
private static final String TAG = "ImageWallpaper";
private static final String GL_LOG_TAG = "ImageWallpaperGL";
- // TODO: Testing purpose, need to remove later, b/123616712.
- private static final String SENSOR_EVENT_AWAKE = "systemui.test.event.awake";
- // TODO: Testing purpose, need to remove later, b/123616712.
- private static final String SENSOR_EVENT_SLEEP = "systemui.test.event.sleep";
private static final boolean DEBUG = false;
private static final String PROPERTY_KERNEL_QEMU = "ro.kernel.qemu";
private static final long DELAY_FORGET_WALLPAPER = 5000;
private WallpaperManager mWallpaperManager;
private DrawableEngine mEngine;
- private GLEngine mGlEngine;
@Override
public void onCreate() {
@@ -84,112 +73,10 @@ public class ImageWallpaper extends WallpaperService {
@Override
public Engine onCreateEngine() {
- mGlEngine = new GLEngine(this);
- return mGlEngine;
+ mEngine = new DrawableEngine();
+ return mEngine;
}
- class GLEngine extends Engine {
- private GLWallpaperSurfaceView mWallpaperSurfaceView;
-
- GLEngine(Context context) {
- mWallpaperSurfaceView = new GLWallpaperSurfaceView(context);
- mWallpaperSurfaceView.setRenderer(
- new ImageWallpaperRenderer(context, mWallpaperSurfaceView));
- mWallpaperSurfaceView.setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY);
- setOffsetNotificationsEnabled(true);
- }
-
- @Override
- public void onAmbientModeChanged(boolean inAmbientMode, long animationDuration) {
- if (mWallpaperSurfaceView != null) {
- mWallpaperSurfaceView.notifyAmbientModeChanged(inAmbientMode);
- }
- }
-
- @Override
- public void onOffsetsChanged(float xOffset, float yOffset, float xOffsetStep,
- float yOffsetStep, int xPixelOffset, int yPixelOffset) {
- if (mWallpaperSurfaceView != null) {
- mWallpaperSurfaceView.notifyOffsetsChanged(xOffset, yOffset);
- }
- }
-
- private class GLWallpaperSurfaceView extends GLSurfaceView implements ImageGLView {
- private SensorEventListener mEventListener;
- private WallpaperStatusListener mWallpaperChangedListener;
-
- // TODO: Testing purpose, need to remove later, b/123616712.
- /**
- * For testing only: adb shell am broadcast -a <INTENT>
- */
- private final BroadcastReceiver mReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- if (intent == null) {
- return;
- }
- switch (intent.getAction()) {
- case SENSOR_EVENT_AWAKE:
- notifySensorEvents(true);
- break;
- case SENSOR_EVENT_SLEEP:
- notifySensorEvents(false);
- break;
- }
- }
- };
-
- GLWallpaperSurfaceView(Context context) {
- super(context);
- setEGLContextClientVersion(2);
- // TODO: Testing purpose, need to remove later, b/123616712.
- if (Build.IS_DEBUGGABLE) {
- IntentFilter filter = new IntentFilter();
- filter.addAction(SENSOR_EVENT_AWAKE);
- filter.addAction(SENSOR_EVENT_SLEEP);
- registerReceiver(mReceiver, filter);
- }
- }
-
- @Override
- public SurfaceHolder getHolder() {
- return getSurfaceHolder();
- }
-
- @Override
- public void setRenderer(Renderer renderer) {
- super.setRenderer(renderer);
- mEventListener = (SensorEventListener) renderer;
- mWallpaperChangedListener = (WallpaperStatusListener) renderer;
- }
-
- private void notifySensorEvents(boolean reach) {
- if (mEventListener != null) {
- mEventListener.onSensorEvent(reach);
- }
- }
-
- private void notifyAmbientModeChanged(boolean inAmbient) {
- if (mWallpaperChangedListener != null) {
- mWallpaperChangedListener.onAmbientModeChanged(inAmbient);
- }
- }
-
- private void notifyOffsetsChanged(float xOffset, float yOffset) {
- if (mWallpaperChangedListener != null) {
- mWallpaperChangedListener.onOffsetsChanged(
- xOffset, yOffset, getHolder().getSurfaceFrame());
- }
- }
-
- @Override
- public void render() {
- requestRender();
- }
- }
- }
-
- // TODO: Remove this engine, tracking on b/123617158.
class DrawableEngine extends Engine {
private final Runnable mUnloadWallpaperCallback = () -> {
unloadWallpaper(false /* forgetSize */);
@@ -677,46 +564,4 @@ public class ImageWallpaper extends WallpaperService {
}
}
}
-
- /**
- * A listener to trace sensor event.
- */
- public interface SensorEventListener {
-
- /**
- * Called back while sensor event comes.
- * @param reach The status of sensor.
- */
- void onSensorEvent(boolean reach);
- }
-
- /**
- * A listener to trace status of image wallpaper.
- */
- public interface WallpaperStatusListener {
-
- /**
- * Called back while ambient mode changes.
- * @param inAmbientMode true if is in ambient mode, false otherwise.
- */
- void onAmbientModeChanged(boolean inAmbientMode);
-
- /**
- * Called back while wallpaper offsets.
- * @param xOffset The offset portion along x.
- * @param yOffset The offset portion along y.
- */
- void onOffsetsChanged(float xOffset, float yOffset, Rect frame);
- }
-
- /**
- * An abstraction for view of GLRenderer.
- */
- public interface ImageGLView {
-
- /**
- * Ask the view to render.
- */
- void render();
- }
}
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
index d6a46a9e3458..6877f5ed6b26 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
@@ -16,6 +16,10 @@
package com.android.systemui.bubbles;
+import static android.content.pm.ActivityInfo.DOCUMENT_LAUNCH_ALWAYS;
+import static android.util.StatsLog.BUBBLE_DEVELOPER_ERROR_REPORTED__ERROR__ACTIVITY_INFO_MISSING;
+import static android.util.StatsLog.BUBBLE_DEVELOPER_ERROR_REPORTED__ERROR__ACTIVITY_INFO_NOT_RESIZABLE;
+import static android.util.StatsLog.BUBBLE_DEVELOPER_ERROR_REPORTED__ERROR__DOCUMENT_LAUNCH_NOT_ALWAYS;
import static android.view.View.INVISIBLE;
import static android.view.View.VISIBLE;
import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
@@ -26,17 +30,16 @@ import static com.android.systemui.statusbar.notification.NotificationAlertingMa
import android.annotation.Nullable;
import android.app.INotificationManager;
import android.app.Notification;
-import android.app.NotificationChannel;
import android.app.PendingIntent;
import android.content.Context;
import android.content.pm.ActivityInfo;
import android.graphics.Point;
import android.graphics.Rect;
-import android.os.RemoteException;
import android.os.ServiceManager;
import android.provider.Settings;
import android.service.notification.StatusBarNotification;
import android.util.Log;
+import android.util.StatsLog;
import android.view.LayoutInflater;
import android.view.ViewGroup;
import android.view.WindowManager;
@@ -427,11 +430,15 @@ public class BubbleController implements BubbleExpandedView.OnBubbleBlockedListe
@Nullable
private PendingIntent getValidBubbleIntent(NotificationEntry notif) {
Notification notification = notif.notification.getNotification();
+ String packageName = notif.notification.getPackageName();
Notification.BubbleMetadata data = notif.getBubbleMetadata();
- if (data != null && canLaunchInActivityView(data.getIntent())) {
+ if (data != null && canLaunchInActivityView(data.getIntent(),
+ true /* enable logging for bubbles */, packageName)) {
return data.getIntent();
- } else if (shouldUseContentIntent(mContext)
- && canLaunchInActivityView(notification.contentIntent)) {
+ }
+ if (shouldUseContentIntent(mContext)
+ && canLaunchInActivityView(notification.contentIntent,
+ false /* disable logging for notifications */, packageName)) {
Log.d(TAG, "[addBubble " + notif.key
+ "]: No appOverlayIntent, using contentIntent.");
return notification.contentIntent;
@@ -442,16 +449,41 @@ public class BubbleController implements BubbleExpandedView.OnBubbleBlockedListe
/**
* Whether an intent is properly configured to display in an {@link android.app.ActivityView}.
+ *
+ * @param intent the pending intent of the bubble.
+ * @param enableLogging whether bubble developer error should be logged.
+ * @param packageName the notification package name for this bubble.
+ * @return
*/
- private boolean canLaunchInActivityView(PendingIntent intent) {
+ private boolean canLaunchInActivityView(PendingIntent intent, boolean enableLogging,
+ String packageName) {
if (intent == null) {
return false;
}
ActivityInfo info =
intent.getIntent().resolveActivityInfo(mContext.getPackageManager(), 0);
- return info != null
- && ActivityInfo.isResizeableMode(info.resizeMode)
- && (info.flags & ActivityInfo.FLAG_ALLOW_EMBEDDED) != 0;
+ if (info == null) {
+ if (enableLogging) {
+ StatsLog.write(StatsLog.BUBBLE_DEVELOPER_ERROR_REPORTED, packageName,
+ BUBBLE_DEVELOPER_ERROR_REPORTED__ERROR__ACTIVITY_INFO_MISSING);
+ }
+ return false;
+ }
+ if (!ActivityInfo.isResizeableMode(info.resizeMode)) {
+ if (enableLogging) {
+ StatsLog.write(StatsLog.BUBBLE_DEVELOPER_ERROR_REPORTED, packageName,
+ BUBBLE_DEVELOPER_ERROR_REPORTED__ERROR__ACTIVITY_INFO_NOT_RESIZABLE);
+ }
+ return false;
+ }
+ if (info.documentLaunchMode != DOCUMENT_LAUNCH_ALWAYS) {
+ if (enableLogging) {
+ StatsLog.write(StatsLog.BUBBLE_DEVELOPER_ERROR_REPORTED, packageName,
+ BUBBLE_DEVELOPER_ERROR_REPORTED__ERROR__DOCUMENT_LAUNCH_NOT_ALWAYS);
+ }
+ return false;
+ }
+ return (info.flags & ActivityInfo.FLAG_ALLOW_EMBEDDED) != 0;
}
/**
diff --git a/packages/SystemUI/src/com/android/systemui/doze/DozeService.java b/packages/SystemUI/src/com/android/systemui/doze/DozeService.java
index 4557b4de4901..d06feedfd9aa 100644
--- a/packages/SystemUI/src/com/android/systemui/doze/DozeService.java
+++ b/packages/SystemUI/src/com/android/systemui/doze/DozeService.java
@@ -110,7 +110,8 @@ public class DozeService extends DreamService
@Override
public void requestWakeUp() {
PowerManager pm = getSystemService(PowerManager.class);
- pm.wakeUp(SystemClock.uptimeMillis(), "com.android.systemui:NODOZE");
+ pm.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_GESTURE,
+ "com.android.systemui:NODOZE");
}
@Override
diff --git a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLProgram.java b/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLProgram.java
deleted file mode 100644
index d03b00bcfc85..000000000000
--- a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLProgram.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.systemui.glwallpaper;
-
-import static android.opengl.GLES20.GL_FRAGMENT_SHADER;
-import static android.opengl.GLES20.GL_VERTEX_SHADER;
-import static android.opengl.GLES20.glAttachShader;
-import static android.opengl.GLES20.glCompileShader;
-import static android.opengl.GLES20.glCreateProgram;
-import static android.opengl.GLES20.glCreateShader;
-import static android.opengl.GLES20.glGetAttribLocation;
-import static android.opengl.GLES20.glGetUniformLocation;
-import static android.opengl.GLES20.glLinkProgram;
-import static android.opengl.GLES20.glShaderSource;
-import static android.opengl.GLES20.glUseProgram;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.util.Log;
-
-import java.io.BufferedReader;
-import java.io.IOException;
-import java.io.InputStreamReader;
-
-/**
- * This class takes charge of linking shader codes and then return a handle for OpenGL ES program.
- */
-class ImageGLProgram {
- private static final String TAG = ImageGLProgram.class.getSimpleName();
-
- private Context mContext;
- private int mProgramHandle;
-
- ImageGLProgram(Context context) {
- mContext = context.getApplicationContext();
- }
-
- private int loadShaderProgram(int vertexId, int fragmentId) {
- final String vertexSrc = getShaderResource(vertexId);
- final String fragmentSrc = getShaderResource(fragmentId);
- final int vertexHandle = getShaderHandle(GL_VERTEX_SHADER, vertexSrc);
- final int fragmentHandle = getShaderHandle(GL_FRAGMENT_SHADER, fragmentSrc);
- return getProgramHandle(vertexHandle, fragmentHandle);
- }
-
- private String getShaderResource(int shaderId) {
- Resources res = mContext.getResources();
- StringBuilder code = new StringBuilder();
-
- try (BufferedReader reader = new BufferedReader(
- new InputStreamReader(res.openRawResource(shaderId)))) {
- String nextLine;
- while ((nextLine = reader.readLine()) != null) {
- code.append(nextLine).append("\n");
- }
- } catch (IOException | Resources.NotFoundException ex) {
- Log.d(TAG, "Can not read the shader source", ex);
- code = null;
- }
-
- return code == null ? "" : code.toString();
- }
-
- private int getShaderHandle(int type, String src) {
- final int shader = glCreateShader(type);
- if (shader == 0) {
- Log.d(TAG, "Create shader failed, type=" + type);
- return 0;
- }
- glShaderSource(shader, src);
- glCompileShader(shader);
- return shader;
- }
-
- private int getProgramHandle(int vertexHandle, int fragmentHandle) {
- final int program = glCreateProgram();
- if (program == 0) {
- Log.d(TAG, "Can not create OpenGL ES program");
- return 0;
- }
-
- glAttachShader(program, vertexHandle);
- glAttachShader(program, fragmentHandle);
- glLinkProgram(program);
- return program;
- }
-
- boolean useGLProgram(int vertexResId, int fragmentResId) {
- mProgramHandle = loadShaderProgram(vertexResId, fragmentResId);
- glUseProgram(mProgramHandle);
- return true;
- }
-
- int getAttributeHandle(String name) {
- return glGetAttribLocation(mProgramHandle, name);
- }
-
- int getUniformHandle(String name) {
- return glGetUniformLocation(mProgramHandle, name);
- }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLWallpaper.java b/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLWallpaper.java
deleted file mode 100644
index 4e07872c9456..000000000000
--- a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageGLWallpaper.java
+++ /dev/null
@@ -1,245 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.systemui.glwallpaper;
-
-import static android.opengl.GLES20.GL_FLOAT;
-import static android.opengl.GLES20.GL_LINEAR;
-import static android.opengl.GLES20.GL_TEXTURE0;
-import static android.opengl.GLES20.GL_TEXTURE_2D;
-import static android.opengl.GLES20.GL_TEXTURE_MAG_FILTER;
-import static android.opengl.GLES20.GL_TEXTURE_MIN_FILTER;
-import static android.opengl.GLES20.GL_TRIANGLES;
-import static android.opengl.GLES20.glActiveTexture;
-import static android.opengl.GLES20.glBindTexture;
-import static android.opengl.GLES20.glDrawArrays;
-import static android.opengl.GLES20.glEnableVertexAttribArray;
-import static android.opengl.GLES20.glGenTextures;
-import static android.opengl.GLES20.glTexParameteri;
-import static android.opengl.GLES20.glUniform1i;
-import static android.opengl.GLES20.glVertexAttribPointer;
-
-import android.graphics.Bitmap;
-import android.opengl.GLUtils;
-import android.util.Log;
-
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-import java.nio.FloatBuffer;
-
-/**
- * This class takes charge of the geometry data like vertices and texture coordinates.
- * It delivers these data to opengl runtime and triggers draw calls if necessary.
- */
-class ImageGLWallpaper {
- private static final String TAG = ImageGLWallpaper.class.getSimpleName();
-
- static final String A_POSITION = "aPosition";
- static final String A_TEXTURE_COORDINATES = "aTextureCoordinates";
- static final String U_CENTER_REVEAL = "uCenterReveal";
- static final String U_REVEAL = "uReveal";
- static final String U_AOD2OPACITY = "uAod2Opacity";
- static final String U_TEXTURE = "uTexture";
- static final String U_AOD_MODE = "uAodMode";
-
- private static final int HANDLE_UNDEFINED = -1;
- private static final int POSITION_COMPONENT_COUNT = 2;
- private static final int TEXTURE_COMPONENT_COUNT = 2;
- private static final int BYTES_PER_FLOAT = 4;
-
- // Vertices to define the square with 2 triangles.
- private static final float[] VERTICES = {
- -1.0f, -1.0f,
- +1.0f, -1.0f,
- +1.0f, +1.0f,
- +1.0f, +1.0f,
- -1.0f, +1.0f,
- -1.0f, -1.0f
- };
-
- // Texture coordinates that maps to vertices.
- private static final float[] TEXTURES = {
- 0f, 1f,
- 1f, 1f,
- 1f, 0f,
- 1f, 0f,
- 0f, 0f,
- 0f, 1f
- };
-
- private final FloatBuffer mVertexBuffer;
- private final FloatBuffer mTextureBuffer;
- private final ImageGLProgram mProgram;
-
- private int mAttrPosition;
- private int mAttrTextureCoordinates;
- private int mUniAod2Opacity;
- private int mUniAodMode;
- private int mUniCenterReveal;
- private int mUniReveal;
- private int mUniTexture;
- private int mTextureId;
-
- ImageGLWallpaper(ImageGLProgram program) {
- mProgram = program;
-
- // Create an float array in opengles runtime (native) and put vertex data.
- mVertexBuffer = ByteBuffer.allocateDirect(VERTICES.length * BYTES_PER_FLOAT)
- .order(ByteOrder.nativeOrder())
- .asFloatBuffer();
- mVertexBuffer.put(VERTICES);
- mVertexBuffer.position(0);
-
- // Create an float array in opengles runtime (native) and put texture data.
- mTextureBuffer = ByteBuffer.allocateDirect(TEXTURES.length * BYTES_PER_FLOAT)
- .order(ByteOrder.nativeOrder())
- .asFloatBuffer();
- mTextureBuffer.put(TEXTURES);
- mTextureBuffer.position(0);
- }
-
- void setup() {
- setupAttributes();
- setupUniforms();
- }
-
- private void setupAttributes() {
- mAttrPosition = mProgram.getAttributeHandle(A_POSITION);
- mVertexBuffer.position(0);
- glVertexAttribPointer(mAttrPosition, POSITION_COMPONENT_COUNT, GL_FLOAT,
- false, 0, mVertexBuffer);
- glEnableVertexAttribArray(mAttrPosition);
-
- mAttrTextureCoordinates = mProgram.getAttributeHandle(A_TEXTURE_COORDINATES);
- mTextureBuffer.position(0);
- glVertexAttribPointer(mAttrTextureCoordinates, TEXTURE_COMPONENT_COUNT, GL_FLOAT,
- false, 0, mTextureBuffer);
- glEnableVertexAttribArray(mAttrTextureCoordinates);
- }
-
- private void setupUniforms() {
- mUniAod2Opacity = mProgram.getUniformHandle(U_AOD2OPACITY);
- mUniAodMode = mProgram.getUniformHandle(U_AOD_MODE);
- mUniCenterReveal = mProgram.getUniformHandle(U_CENTER_REVEAL);
- mUniReveal = mProgram.getUniformHandle(U_REVEAL);
- mUniTexture = mProgram.getUniformHandle(U_TEXTURE);
- }
-
- int getHandle(String name) {
- switch (name) {
- case A_POSITION:
- return mAttrPosition;
- case A_TEXTURE_COORDINATES:
- return mAttrTextureCoordinates;
- case U_AOD2OPACITY:
- return mUniAod2Opacity;
- case U_AOD_MODE:
- return mUniAodMode;
- case U_CENTER_REVEAL:
- return mUniCenterReveal;
- case U_REVEAL:
- return mUniReveal;
- case U_TEXTURE:
- return mUniTexture;
- default:
- return HANDLE_UNDEFINED;
- }
- }
-
- void draw() {
- glDrawArrays(GL_TRIANGLES, 0, VERTICES.length / 2);
- }
-
- void setupTexture(Bitmap bitmap) {
- final int[] tids = new int[1];
-
- if (bitmap == null) {
- Log.w(TAG, "setupTexture: invalid bitmap");
- return;
- }
-
- // Generate one texture object and store the id in tids[0].
- glGenTextures(1, tids, 0);
- if (tids[0] == 0) {
- Log.w(TAG, "setupTexture: glGenTextures() failed");
- return;
- }
-
- // Bind a named texture to a texturing target.
- glBindTexture(GL_TEXTURE_2D, tids[0]);
- // Load the bitmap data and copy it over into the texture object that is currently bound.
- GLUtils.texImage2D(GL_TEXTURE_2D, 0, bitmap, 0);
- // Use bilinear texture filtering when minification.
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
- // Use bilinear texture filtering when magnification.
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-
- mTextureId = tids[0];
- }
-
- void useTexture() {
- // Set the active texture unit to texture unit 0.
- glActiveTexture(GL_TEXTURE0);
- // Bind the texture to this unit.
- glBindTexture(GL_TEXTURE_2D, mTextureId);
- // Let the texture sampler in fragment shader to read form this texture unit.
- glUniform1i(mUniTexture, 0);
- }
-
- void adjustTextureCoordinates(Bitmap bitmap, int surfaceWidth, int surfaceHeight,
- float xOffset, float yOffset) {
- if (bitmap == null) {
- Log.d(TAG, "adjustTextureCoordinates: invalid bitmap");
- return;
- }
-
- float ratioW = 1f;
- float ratioH = 1f;
- int bitmapWidth = bitmap.getWidth();
- int bitmapHeight = bitmap.getHeight();
-
- boolean adjustWidth = bitmapWidth > surfaceWidth;
- if (adjustWidth) {
- ratioW = (float) surfaceWidth / bitmapWidth;
- float referenceX = xOffset + ratioW > 1f ? 1f - ratioW : xOffset;
- for (int i = 0; i < TEXTURES.length; i += 2) {
- if (i == 2 || i == 4 || i == 6) {
- TEXTURES[i] = Math.min(1f, referenceX + ratioW);
- } else {
- TEXTURES[i] = referenceX;
- }
- }
- }
-
- boolean adjustHeight = bitmapHeight > surfaceHeight;
- if (adjustHeight) {
- ratioH = (float) surfaceHeight / bitmapHeight;
- float referenceY = yOffset + ratioH > 1f ? 1f - ratioH : yOffset;
- for (int i = 1; i < TEXTURES.length; i += 2) {
- if (i == 1 || i == 3 || i == 11) {
- TEXTURES[i] = Math.min(1f, referenceY + ratioH);
- } else {
- TEXTURES[i] = referenceY;
- }
- }
- }
-
- if (adjustWidth || adjustHeight) {
- mTextureBuffer.put(TEXTURES);
- mTextureBuffer.position(0);
- }
- }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageProcessHelper.java b/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageProcessHelper.java
deleted file mode 100644
index 477e7d7ebf72..000000000000
--- a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageProcessHelper.java
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.systemui.glwallpaper;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorMatrix;
-import android.graphics.ColorMatrixColorFilter;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.os.AsyncTask;
-import android.os.Handler;
-import android.os.Handler.Callback;
-import android.os.Message;
-import android.util.Log;
-
-/**
- * A helper class that computes histogram and percentile 85 from a bitmap.
- * Percentile 85 will be computed each time the user picks a new image wallpaper.
- */
-class ImageProcessHelper {
- private static final String TAG = ImageProcessHelper.class.getSimpleName();
- private static final float DEFAULT_PER85 = 0.8f;
- private static final int MSG_UPDATE_PER85 = 1;
-
- /**
- * This color matrix will be applied to each pixel to get luminance from rgb by below formula:
- * Luminance = .2126f * r + .7152f * g + .0722f * b.
- */
- private static final float[] LUMINOSITY_MATRIX = new float[] {
- .2126f, .0000f, .0000f, .0000f, .0000f,
- .0000f, .7152f, .0000f, .0000f, .0000f,
- .0000f, .0000f, .0722f, .0000f, .0000f,
- .0000f, .0000f, .0000f, 1.000f, .0000f
- };
-
- private final Handler mHandler = new Handler(new Callback() {
- @Override
- public boolean handleMessage(Message msg) {
- switch (msg.what) {
- case MSG_UPDATE_PER85:
- mPer85 = (float) msg.obj;
- return true;
- default:
- return false;
- }
- }
- });
-
- private float mPer85 = DEFAULT_PER85;
-
- void startComputingPercentile85(Bitmap bitmap) {
- new Per85ComputeTask(mHandler).execute(bitmap);
- }
-
- float getPercentile85() {
- return mPer85;
- }
-
- private static class Per85ComputeTask extends AsyncTask<Bitmap, Void, Float> {
- private Handler mUpdateHandler;
-
- Per85ComputeTask(Handler handler) {
- super(handler);
- mUpdateHandler = handler;
- }
-
- @Override
- protected Float doInBackground(Bitmap... bitmaps) {
- Bitmap bitmap = bitmaps[0];
- if (bitmap != null) {
- int[] histogram = processHistogram(bitmap);
- return computePercentile85(bitmap, histogram);
- }
- Log.e(TAG, "Per85ComputeTask: Can't get bitmap");
- return DEFAULT_PER85;
- }
-
- @Override
- protected void onPostExecute(Float result) {
- Message msg = mUpdateHandler.obtainMessage(MSG_UPDATE_PER85, result);
- mUpdateHandler.sendMessage(msg);
- }
-
- private int[] processHistogram(Bitmap bitmap) {
- int width = bitmap.getWidth();
- int height = bitmap.getHeight();
-
- Bitmap target = Bitmap.createBitmap(width, height, bitmap.getConfig());
- Canvas canvas = new Canvas(target);
- ColorMatrix cm = new ColorMatrix(LUMINOSITY_MATRIX);
- Paint paint = new Paint();
- paint.setColorFilter(new ColorMatrixColorFilter(cm));
- canvas.drawBitmap(bitmap, new Matrix(), paint);
-
- // TODO: Fine tune the performance here, tracking on b/123615079.
- int[] histogram = new int[256];
- for (int row = 0; row < height; row++) {
- for (int col = 0; col < width; col++) {
- int pixel = target.getPixel(col, row);
- int y = Color.red(pixel) + Color.green(pixel) + Color.blue(pixel);
- histogram[y]++;
- }
- }
-
- return histogram;
- }
-
- private float computePercentile85(Bitmap bitmap, int[] histogram) {
- float per85 = DEFAULT_PER85;
- int pixelCount = bitmap.getWidth() * bitmap.getHeight();
- float[] acc = new float[256];
- for (int i = 0; i < acc.length; i++) {
- acc[i] = (float) histogram[i] / pixelCount;
- float prev = i == 0 ? 0f : acc[i - 1];
- float next = acc[i];
- float idx = (float) (i + 1) / 255;
- float sum = prev + next;
- if (prev < 0.85f && sum >= 0.85f) {
- per85 = idx;
- }
- if (i > 0) {
- acc[i] += acc[i - 1];
- }
- }
- return per85;
- }
- }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageRevealHelper.java b/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageRevealHelper.java
deleted file mode 100644
index 787972c08e4a..000000000000
--- a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageRevealHelper.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.systemui.glwallpaper;
-
-import android.animation.Animator;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.ValueAnimator;
-
-import com.android.systemui.Interpolators;
-
-/**
- * Use ValueAnimator and appropriate interpolator to control the progress of reveal transition.
- * The transition will happen while getting awake and quit events.
- */
-class ImageRevealHelper {
- private static final String TAG = ImageRevealHelper.class.getSimpleName();
- private static final float MAX_REVEAL = 0f;
- private static final float MIN_REVEAL = 1f;
- private static final int REVEAL_DURATION = 1000;
-
- private final ValueAnimator mAnimator;
- private final RevealStateListener mRevealListener;
- private float mReveal = MIN_REVEAL;
- private boolean mAwake = false;
-
- ImageRevealHelper(RevealStateListener listener) {
- mRevealListener = listener;
- mAnimator = ValueAnimator.ofFloat();
- mAnimator.setDuration(REVEAL_DURATION);
- mAnimator.setInterpolator(Interpolators.FAST_OUT_SLOW_IN);
- mAnimator.addUpdateListener(animator -> {
- mReveal = (float) animator.getAnimatedValue();
- if (mRevealListener != null) {
- mRevealListener.onRevealStateChanged();
- }
- });
- mAnimator.addListener(new AnimatorListenerAdapter() {
- private boolean mIsCanceled;
-
- @Override
- public void onAnimationCancel(Animator animation) {
- mIsCanceled = true;
- }
-
- @Override
- public void onAnimationEnd(Animator animation) {
- if (!mIsCanceled) {
- mAwake = !mAwake;
- }
- mIsCanceled = false;
- }
- });
- }
-
- private void animate() {
- mAnimator.cancel();
- mAnimator.setFloatValues(mReveal, !mAwake ? MIN_REVEAL : MAX_REVEAL);
- mAnimator.start();
- }
-
- public float getReveal() {
- return mReveal;
- }
-
- public boolean isAwake() {
- return mAwake;
- }
-
- void updateAwake(boolean awake) {
- mAwake = awake;
- animate();
- }
-
- void sleep() {
- mReveal = MIN_REVEAL;
- mAwake = false;
- }
-
- /**
- * A listener to trace value changes of reveal.
- */
- public interface RevealStateListener {
-
- /**
- * Called back while reveal status changes.
- */
- void onRevealStateChanged();
- }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageWallpaperRenderer.java b/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageWallpaperRenderer.java
deleted file mode 100644
index 8916b28f201a..000000000000
--- a/packages/SystemUI/src/com/android/systemui/glwallpaper/ImageWallpaperRenderer.java
+++ /dev/null
@@ -1,153 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.systemui.glwallpaper;
-
-import static android.opengl.GLES20.GL_COLOR_BUFFER_BIT;
-import static android.opengl.GLES20.glClear;
-import static android.opengl.GLES20.glClearColor;
-import static android.opengl.GLES20.glUniform1f;
-import static android.opengl.GLES20.glUniform1i;
-import static android.opengl.GLES20.glViewport;
-
-import android.app.WallpaperManager;
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.opengl.GLSurfaceView;
-import android.util.Log;
-
-import com.android.systemui.ImageWallpaper;
-import com.android.systemui.ImageWallpaper.ImageGLView;
-import com.android.systemui.R;
-
-import javax.microedition.khronos.egl.EGLConfig;
-import javax.microedition.khronos.opengles.GL10;
-
-/**
- * A GL renderer for image wallpaper.
- */
-public class ImageWallpaperRenderer implements GLSurfaceView.Renderer,
- ImageWallpaper.SensorEventListener, ImageWallpaper.WallpaperStatusListener,
- ImageRevealHelper.RevealStateListener {
- private static final String TAG = ImageWallpaperRenderer.class.getSimpleName();
-
- private final WallpaperManager mWallpaperManager;
- private final ImageGLProgram mProgram;
- private final ImageGLWallpaper mWallpaper;
- private final ImageProcessHelper mImageProcessHelper;
- private final ImageRevealHelper mImageRevealHelper;
- private final ImageGLView mGLView;
- private boolean mIsInAmbientMode;
- private float mXOffset = 0f;
- private float mYOffset = 0f;
-
- public ImageWallpaperRenderer(Context context, ImageGLView glView) {
- mWallpaperManager = context.getSystemService(WallpaperManager.class);
- if (mWallpaperManager == null) {
- Log.w(TAG, "WallpaperManager not available");
- }
-
- mProgram = new ImageGLProgram(context);
- mWallpaper = new ImageGLWallpaper(mProgram);
- mImageProcessHelper = new ImageProcessHelper();
- mImageRevealHelper = new ImageRevealHelper(this);
- mGLView = glView;
-
- if (mWallpaperManager != null) {
- // Compute per85 as transition threshold, this is an async work.
- mImageProcessHelper.startComputingPercentile85(mWallpaperManager.getBitmap());
- }
- }
-
- @Override
- public void onSurfaceCreated(GL10 gl, EGLConfig config) {
- glClearColor(0f, 0f, 0f, 1.0f);
- mProgram.useGLProgram(
- R.raw.image_wallpaper_vertex_shader, R.raw.image_wallpaper_fragment_shader);
- mWallpaper.setup();
- mWallpaper.setupTexture(mWallpaperManager.getBitmap());
- }
-
- @Override
- public void onSurfaceChanged(GL10 gl, int width, int height) {
- glViewport(0, 0, width, height);
- mWallpaper.adjustTextureCoordinates(mWallpaperManager.getBitmap(),
- width, height, mXOffset, mYOffset);
- }
-
- @Override
- public void onDrawFrame(GL10 gl) {
- float threshold = mImageProcessHelper.getPercentile85();
- float reveal = mImageRevealHelper.getReveal();
-
- glClear(GL_COLOR_BUFFER_BIT);
-
- glUniform1f(mWallpaper.getHandle(ImageGLWallpaper.U_AOD2OPACITY), .25f);
- glUniform1f(mWallpaper.getHandle(ImageGLWallpaper.U_CENTER_REVEAL), threshold);
- glUniform1f(mWallpaper.getHandle(ImageGLWallpaper.U_REVEAL), reveal);
- glUniform1i(mWallpaper.getHandle(ImageGLWallpaper.U_AOD_MODE), mIsInAmbientMode ? 1 : 0);
-
- mWallpaper.useTexture();
- mWallpaper.draw();
- }
-
- @Override
- public void onSensorEvent(boolean awake) {
- mImageRevealHelper.updateAwake(awake);
- }
-
- @Override
- public void onAmbientModeChanged(boolean inAmbientMode) {
- mIsInAmbientMode = inAmbientMode;
- if (inAmbientMode) {
- mImageRevealHelper.sleep();
- }
- requestRender();
- }
-
- @Override
- public void onOffsetsChanged(float xOffset, float yOffset, Rect frame) {
- if (frame == null || mWallpaperManager == null
- || (xOffset == mXOffset && yOffset == mYOffset)) {
- return;
- }
-
- Bitmap bitmap = mWallpaperManager.getBitmap();
- if (bitmap == null) {
- return;
- }
-
- int width = frame.width();
- int height = frame.height();
- mXOffset = xOffset;
- mYOffset = yOffset;
-
- mWallpaper.adjustTextureCoordinates(bitmap, width, height, mXOffset, mYOffset);
- requestRender();
- }
-
- @Override
- public void onRevealStateChanged() {
- requestRender();
- }
-
- private void requestRender() {
- if (mGLView != null) {
- mGLView.render();
- }
- }
-}
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java
index 4527f73ab118..66cfadf9d6e8 100644
--- a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java
+++ b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java
@@ -884,6 +884,7 @@ public class KeyguardViewMediator extends SystemUI {
// Just to make sure, make sure the device is awake.
mContext.getSystemService(PowerManager.class).wakeUp(SystemClock.uptimeMillis(),
+ PowerManager.WAKE_REASON_CAMERA_LAUNCH,
"com.android.systemui:CAMERA_GESTURE_PREVENT_LOCK");
mPendingLock = false;
mPendingReset = false;
@@ -1854,8 +1855,9 @@ public class KeyguardViewMediator extends SystemUI {
// It's possible that the device was unlocked in a dream state. It's time to wake up.
if (mAodShowing) {
- PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
- pm.wakeUp(SystemClock.uptimeMillis(), "com.android.systemui:BOUNCER_DOZING");
+ PowerManager pm = mContext.getSystemService(PowerManager.class);
+ pm.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_GESTURE,
+ "com.android.systemui:BOUNCER_DOZING");
}
synchronized (KeyguardViewMediator.this) {
diff --git a/packages/SystemUI/src/com/android/systemui/privacy/OngoingPrivacyDialog.kt b/packages/SystemUI/src/com/android/systemui/privacy/OngoingPrivacyDialog.kt
index fa1426e45142..cff7fe449be1 100644
--- a/packages/SystemUI/src/com/android/systemui/privacy/OngoingPrivacyDialog.kt
+++ b/packages/SystemUI/src/com/android/systemui/privacy/OngoingPrivacyDialog.kt
@@ -69,7 +69,7 @@ class OngoingPrivacyDialog constructor(
setPositiveButton(R.string.ongoing_privacy_dialog_ok, null)
setNeutralButton(R.string.ongoing_privacy_dialog_open_settings,
object : DialogInterface.OnClickListener {
- val intent = Intent(Settings.ACTION_ENTERPRISE_PRIVACY_SETTINGS).putExtra(
+ val intent = Intent(Settings.ACTION_PRIVACY_SETTINGS).putExtra(
Intent.EXTRA_DURATION_MILLIS, TimeUnit.MINUTES.toMillis(1))
@Suppress("DEPRECATION")
@@ -167,7 +167,7 @@ class OngoingPrivacyDialog constructor(
// Check if package exists
context.packageManager.getPackageInfo(app.packageName, 0)
item.setOnClickListener(object : View.OnClickListener {
- val intent = Intent(Intent.ACTION_REVIEW_APP_PERMISSION_USAGE)
+ val intent = Intent(Intent.ACTION_MANAGE_APP_PERMISSIONS)
.putExtra(Intent.EXTRA_PACKAGE_NAME, app.packageName)
.putExtra(Intent.EXTRA_USER, UserHandle.getUserHandleForUid(app.uid))
override fun onClick(v: View?) {
diff --git a/packages/SystemUI/src/com/android/systemui/qs/tiles/NightDisplayTile.java b/packages/SystemUI/src/com/android/systemui/qs/tiles/NightDisplayTile.java
index de78d3376500..effa935c5c20 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/tiles/NightDisplayTile.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/tiles/NightDisplayTile.java
@@ -22,6 +22,7 @@ import android.annotation.Nullable;
import android.app.ActivityManager;
import android.content.Intent;
import android.hardware.display.ColorDisplayManager;
+import android.hardware.display.NightDisplayListener;
import android.metrics.LogMaker;
import android.provider.Settings;
import android.service.quicksettings.Tile;
@@ -31,7 +32,6 @@ import android.widget.Switch;
import androidx.annotation.StringRes;
-import com.android.internal.app.ColorDisplayController;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.systemui.R;
import com.android.systemui.plugins.qs.QSTile.BooleanState;
@@ -46,8 +46,9 @@ import java.util.TimeZone;
import javax.inject.Inject;
-public class NightDisplayTile extends QSTileImpl<BooleanState>
- implements ColorDisplayController.Callback {
+/** Quick settings tile: Night display **/
+public class NightDisplayTile extends QSTileImpl<BooleanState> implements
+ NightDisplayListener.Callback {
/**
* Pattern for {@link java.time.format.DateTimeFormatter} used to approximate the time to the
@@ -57,13 +58,15 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
private static final String PATTERN_HOUR_MINUTE = "h:mm a";
private static final String PATTERN_HOUR_NINUTE_24 = "HH:mm";
- private ColorDisplayController mController;
+ private final ColorDisplayManager mManager;
+ private NightDisplayListener mListener;
private boolean mIsListening;
@Inject
public NightDisplayTile(QSHost host) {
super(host);
- mController = new ColorDisplayController(mContext, ActivityManager.getCurrentUser());
+ mManager = mContext.getSystemService(ColorDisplayManager.class);
+ mListener = new NightDisplayListener(mContext, ActivityManager.getCurrentUser());
}
@Override
@@ -81,27 +84,27 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
// Enroll in forced auto mode if eligible.
if ("1".equals(Settings.Global.getString(mContext.getContentResolver(),
Settings.Global.NIGHT_DISPLAY_FORCED_AUTO_MODE_AVAILABLE))
- && mController.getAutoModeRaw() == -1) {
- mController.setAutoMode(ColorDisplayManager.AUTO_MODE_CUSTOM_TIME);
+ && mManager.getNightDisplayAutoModeRaw() == -1) {
+ mManager.setNightDisplayAutoMode(ColorDisplayManager.AUTO_MODE_CUSTOM_TIME);
Log.i("NightDisplayTile", "Enrolled in forced night display auto mode");
}
// Change current activation state.
final boolean activated = !mState.value;
- mController.setActivated(activated);
+ mManager.setNightDisplayActivated(activated);
}
@Override
protected void handleUserSwitch(int newUserId) {
// Stop listening to the old controller.
if (mIsListening) {
- mController.setListener(null);
+ mListener.setCallback(null);
}
// Make a new controller for the new user.
- mController = new ColorDisplayController(mContext, newUserId);
+ mListener = new NightDisplayListener(mContext, newUserId);
if (mIsListening) {
- mController.setListener(this);
+ mListener.setCallback(this);
}
super.handleUserSwitch(newUserId);
@@ -109,7 +112,7 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
@Override
protected void handleUpdateState(BooleanState state, Object arg) {
- state.value = mController.isActivated();
+ state.value = mManager.isNightDisplayActivated();
state.label = mContext.getString(R.string.quick_settings_night_display_label);
state.icon = ResourceIcon.get(com.android.internal.R.drawable.ic_qs_night_display_on);
state.expandedAccessibilityClassName = Switch.class.getName();
@@ -121,12 +124,12 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
}
/**
- * Returns a {@link String} for the secondary label that reflects when the light will be turned
- * on or off based on the current auto mode and night light activated status.
+ * Returns a String for the secondary label that reflects when the light will be turned on or
+ * off based on the current auto mode and night light activated status.
*/
@Nullable
private String getSecondaryLabel(boolean isNightLightActivated) {
- switch(mController.getAutoMode()) {
+ switch (mManager.getNightDisplayAutoMode()) {
case ColorDisplayManager.AUTO_MODE_TWILIGHT:
// Auto mode related to sunrise & sunset. If the light is on, it's guaranteed to be
// turned off at sunrise. If it's off, it's guaranteed to be turned on at sunset.
@@ -143,10 +146,10 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
final DateTimeFormatter toggleTimeFormat;
if (isNightLightActivated) {
- toggleTime = mController.getCustomEndTime();
+ toggleTime = mManager.getNightDisplayCustomEndTime();
toggleTimeStringRes = R.string.quick_settings_secondary_label_until;
} else {
- toggleTime = mController.getCustomStartTime();
+ toggleTime = mManager.getNightDisplayCustomStartTime();
toggleTimeStringRes = R.string.quick_settings_night_secondary_label_on_at;
}
@@ -175,7 +178,8 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
@Override
public LogMaker populate(LogMaker logMaker) {
- return super.populate(logMaker).addTaggedData(FIELD_QS_MODE, mController.getAutoModeRaw());
+ return super.populate(logMaker)
+ .addTaggedData(FIELD_QS_MODE, mManager.getNightDisplayAutoModeRaw());
}
@Override
@@ -187,10 +191,10 @@ public class NightDisplayTile extends QSTileImpl<BooleanState>
protected void handleSetListening(boolean listening) {
mIsListening = listening;
if (listening) {
- mController.setListener(this);
+ mListener.setCallback(this);
refreshState();
} else {
- mController.setListener(null);
+ mListener.setCallback(null);
}
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationRemoteInputManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationRemoteInputManager.java
index 491f310cedf2..b820dc09657a 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/NotificationRemoteInputManager.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/NotificationRemoteInputManager.java
@@ -132,7 +132,8 @@ public class NotificationRemoteInputManager implements Dumpable {
@Override
public boolean onClickHandler(
View view, PendingIntent pendingIntent, RemoteViews.RemoteResponse response) {
- mShadeController.get().wakeUpIfDozing(SystemClock.uptimeMillis(), view);
+ mShadeController.get().wakeUpIfDozing(SystemClock.uptimeMillis(), view,
+ "NOTIFICATION_CLICK");
if (handleRemoteInput(view, pendingIntent)) {
return true;
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationClicker.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationClicker.java
index 49f1a8d6f248..b788f537316b 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationClicker.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationClicker.java
@@ -52,7 +52,7 @@ public final class NotificationClicker implements View.OnClickListener {
return;
}
- mShadeController.wakeUpIfDozing(SystemClock.uptimeMillis(), v);
+ mShadeController.wakeUpIfDozing(SystemClock.uptimeMillis(), v, "NOTIFICATION_CLICK");
final ExpandableNotificationRow row = (ExpandableNotificationRow) v;
final StatusBarNotification sbn = row.getStatusBarNotification();
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java
index b6948fc4bd1f..c7b2fab54fff 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java
@@ -537,7 +537,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
mChosenImportance = IMPORTANCE_LOW;
confirmationText.setText(R.string.notification_channel_silenced);
} else {
- mChosenImportance = IMPORTANCE_HIGH;
+ mChosenImportance = IMPORTANCE_DEFAULT;
confirmationText.setText(R.string.notification_channel_unsilenced);
}
break;
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/AutoTileManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/AutoTileManager.java
index b96c55b37c48..c9be2c8f6703 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/AutoTileManager.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/AutoTileManager.java
@@ -16,11 +16,11 @@ package com.android.systemui.statusbar.phone;
import android.content.Context;
import android.hardware.display.ColorDisplayManager;
+import android.hardware.display.NightDisplayListener;
import android.os.Handler;
import android.provider.Settings.Secure;
import com.android.internal.annotations.VisibleForTesting;
-import com.android.internal.app.ColorDisplayController;
import com.android.systemui.Dependency;
import com.android.systemui.qs.AutoAddTracker;
import com.android.systemui.qs.QSTileHost;
@@ -50,7 +50,7 @@ public class AutoTileManager {
private final HotspotController mHotspotController;
private final DataSaverController mDataSaverController;
private final ManagedProfileController mManagedProfileController;
- private final ColorDisplayController mColorDisplayController;
+ private final NightDisplayListener mNightDisplayListener;
@Inject
public AutoTileManager(Context context, AutoAddTracker autoAddTracker, QSTileHost host,
@@ -58,7 +58,7 @@ public class AutoTileManager {
HotspotController hotspotController,
DataSaverController dataSaverController,
ManagedProfileController managedProfileController,
- ColorDisplayController colorDisplayController) {
+ NightDisplayListener nightDisplayListener) {
mAutoTracker = autoAddTracker;
mContext = context;
mHost = host;
@@ -66,7 +66,7 @@ public class AutoTileManager {
mHotspotController = hotspotController;
mDataSaverController = dataSaverController;
mManagedProfileController = managedProfileController;
- mColorDisplayController = colorDisplayController;
+ mNightDisplayListener = nightDisplayListener;
if (!mAutoTracker.isAdded(HOTSPOT)) {
hotspotController.addCallback(mHotspotCallback);
}
@@ -93,7 +93,7 @@ public class AutoTileManager {
}
if (!mAutoTracker.isAdded(NIGHT)
&& ColorDisplayManager.isNightDisplayAvailable(mContext)) {
- colorDisplayController.setListener(mColorDisplayCallback);
+ nightDisplayListener.setCallback(mNightDisplayCallback);
}
}
@@ -106,7 +106,7 @@ public class AutoTileManager {
mDataSaverController.removeCallback(mDataSaverListener);
mManagedProfileController.removeCallback(mProfileCallback);
if (ColorDisplayManager.isNightDisplayAvailable(mContext)) {
- mColorDisplayController.setListener(null);
+ mNightDisplayListener.setCallback(null);
}
}
@@ -157,8 +157,8 @@ public class AutoTileManager {
};
@VisibleForTesting
- final ColorDisplayController.Callback mColorDisplayCallback =
- new ColorDisplayController.Callback() {
+ final NightDisplayListener.Callback mNightDisplayCallback =
+ new NightDisplayListener.Callback() {
@Override
public void onActivated(boolean activated) {
if (activated) {
@@ -178,7 +178,7 @@ public class AutoTileManager {
if (mAutoTracker.isAdded(NIGHT)) return;
mHost.addTile(NIGHT);
mAutoTracker.setTileAdded(NIGHT);
- mHandler.post(() -> mColorDisplayController.setListener(null));
+ mHandler.post(() -> mNightDisplayListener.setCallback(null));
}
};
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java
index 304d2ee70c35..2162ea70fe84 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java
@@ -232,7 +232,8 @@ public class BiometricUnlockController extends KeyguardUpdateMonitorCallback {
if (DEBUG_BIO_WAKELOCK) {
Log.i(TAG, "bio wakelock: Authenticated, waking up...");
}
- mPowerManager.wakeUp(SystemClock.uptimeMillis(), "android.policy:BIOMETRIC");
+ mPowerManager.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_GESTURE,
+ "android.policy:BIOMETRIC");
}
if (delayWakeUp) {
mKeyguardViewMediator.onWakeAndUnlocking();
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java
index f9262186968f..234a968e9f75 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java
@@ -14,6 +14,7 @@
package com.android.systemui.statusbar.phone;
+import android.annotation.NonNull;
import android.view.View;
import com.android.systemui.statusbar.StatusBarState;
@@ -96,8 +97,9 @@ public interface ShadeController {
*
* @param time when to wake up
* @param view the view requesting the wakeup
+ * @param why the reason for the wake up
*/
- void wakeUpIfDozing(long time, View view);
+ void wakeUpIfDozing(long time, View view, @NonNull String why);
/**
* If secure with redaction: Show bouncer, go to unlocked shade.
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
index 3532af560557..37a0610d4de5 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
@@ -482,7 +482,8 @@ public class StatusBar extends SystemUI implements DemoMode,
updateAodMaskVisibility(deviceSupportsAodWallpaper && aodImageWallpaperEnabled);
// If WallpaperInfo is null, it must be ImageWallpaper.
final boolean supportsAmbientMode = deviceSupportsAodWallpaper
- && (info == null || info.supportsAmbientMode());
+ && (info == null && aodImageWallpaperEnabled
+ || info != null && info.supportsAmbientMode());
mStatusBarWindowController.setWallpaperSupportsAmbientMode(supportsAmbientMode);
mScrimController.setWallpaperSupportsAmbientMode(supportsAmbientMode);
@@ -551,7 +552,7 @@ public class StatusBar extends SystemUI implements DemoMode,
private final View.OnClickListener mGoToLockedShadeListener = v -> {
if (mState == StatusBarState.KEYGUARD) {
- wakeUpIfDozing(SystemClock.uptimeMillis(), v);
+ wakeUpIfDozing(SystemClock.uptimeMillis(), v, "SHADE_CLICK");
goToLockedShade(null);
}
};
@@ -1090,10 +1091,10 @@ public class StatusBar extends SystemUI implements DemoMode,
}
@Override
- public void wakeUpIfDozing(long time, View where) {
+ public void wakeUpIfDozing(long time, View where, String why) {
if (mDozing) {
- PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
- pm.wakeUp(time, "com.android.systemui:NODOZE");
+ PowerManager pm = mContext.getSystemService(PowerManager.class);
+ pm.wakeUp(time, PowerManager.WAKE_REASON_GESTURE, "com.android.systemui:" + why);
mWakeUpComingFromTouch = true;
where.getLocationInWindow(mTmpInt2);
mWakeUpTouchLocation = new PointF(mTmpInt2[0] + where.getWidth() / 2,
@@ -3729,7 +3730,8 @@ public class StatusBar extends SystemUI implements DemoMode,
}
if (!mDeviceInteractive) {
PowerManager pm = mContext.getSystemService(PowerManager.class);
- pm.wakeUp(SystemClock.uptimeMillis(), "com.android.systemui:CAMERA_GESTURE");
+ pm.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_CAMERA_LAUNCH,
+ "com.android.systemui:CAMERA_GESTURE");
mStatusBarKeyguardViewManager.notifyDeviceWakeUpRequested();
}
vibrateForCameraGesture();
@@ -3890,7 +3892,8 @@ public class StatusBar extends SystemUI implements DemoMode,
public void pulseWhileDozing(@NonNull PulseCallback callback, int reason) {
mScrimController.setPulseReason(reason);
if (reason == DozeLog.PULSE_REASON_SENSOR_LONG_PRESS) {
- mPowerManager.wakeUp(SystemClock.uptimeMillis(), "com.android.systemui:NODOZE");
+ mPowerManager.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_GESTURE,
+ "com.android.systemui:LONG_PRESS");
startAssist(new Bundle());
return;
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarWindowView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarWindowView.java
index 8b25c3469abe..c39e17266b56 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarWindowView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarWindowView.java
@@ -112,7 +112,7 @@ public class StatusBarWindowView extends FrameLayout {
mTransparentSrcPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC));
mFalsingManager = FalsingManager.getInstance(context);
mDoubleTapHelper = new DoubleTapHelper(this, active -> {}, () -> {
- mService.wakeUpIfDozing(SystemClock.uptimeMillis(), this);
+ mService.wakeUpIfDozing(SystemClock.uptimeMillis(), this, "DOUBLE_TAP");
return true;
}, null, null);
}
diff --git a/packages/SystemUI/src/com/android/systemui/wallpaper/AodMaskView.java b/packages/SystemUI/src/com/android/systemui/wallpaper/AodMaskView.java
index dd1d0ca06fa8..52cabe278e2d 100644
--- a/packages/SystemUI/src/com/android/systemui/wallpaper/AodMaskView.java
+++ b/packages/SystemUI/src/com/android/systemui/wallpaper/AodMaskView.java
@@ -156,8 +156,6 @@ public class AodMaskView extends ImageView implements StatusBarStateController.S
private boolean checkIfNeedMask() {
// We need mask for ImageWallpaper / LockScreen Wallpaper (Music album art).
- // Because of conflicting with another wallpaper feature,
- // we only support LockScreen wallpaper currently.
return mWallpaperManager.getWallpaperInfo() == null || ScrimState.AOD.hasBackdrop();
}
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java
index 2a64445f342a..105bd9dd8793 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java
@@ -18,7 +18,6 @@ package com.android.systemui.statusbar.notification.row;
import static android.app.NotificationChannel.USER_LOCKED_IMPORTANCE;
import static android.app.NotificationManager.IMPORTANCE_DEFAULT;
-import static android.app.NotificationManager.IMPORTANCE_HIGH;
import static android.app.NotificationManager.IMPORTANCE_LOW;
import static android.app.NotificationManager.IMPORTANCE_MIN;
import static android.app.NotificationManager.IMPORTANCE_NONE;
@@ -1067,7 +1066,7 @@ public class NotificationInfoTest extends SysuiTestCase {
anyString(), eq(TEST_UID), updated.capture());
assertTrue((updated.getValue().getUserLockedFields()
& USER_LOCKED_IMPORTANCE) != 0);
- assertEquals(IMPORTANCE_HIGH, updated.getValue().getImportance());
+ assertEquals(IMPORTANCE_DEFAULT, updated.getValue().getImportance());
}
@Test
@@ -1111,7 +1110,7 @@ public class NotificationInfoTest extends SysuiTestCase {
anyString(), eq(TEST_UID), updated.capture());
assertTrue((updated.getValue().getUserLockedFields()
& USER_LOCKED_IMPORTANCE) != 0);
- assertEquals(IMPORTANCE_HIGH, updated.getValue().getImportance());
+ assertEquals(IMPORTANCE_DEFAULT, updated.getValue().getImportance());
}
@Test
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/AutoTileManagerTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/AutoTileManagerTest.java
index 1ded835e9651..f3740c4d51d0 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/AutoTileManagerTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/AutoTileManagerTest.java
@@ -21,13 +21,13 @@ import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import android.hardware.display.ColorDisplayManager;
+import android.hardware.display.NightDisplayListener;
import android.os.Handler;
import android.support.test.filters.SmallTest;
import android.testing.AndroidTestingRunner;
import android.testing.TestableLooper;
import android.testing.TestableLooper.RunWithLooper;
-import com.android.internal.app.ColorDisplayController;
import com.android.systemui.SysuiTestCase;
import com.android.systemui.qs.AutoAddTracker;
import com.android.systemui.qs.QSTileHost;
@@ -58,7 +58,7 @@ public class AutoTileManagerTest extends SysuiTestCase {
mock(HotspotController.class),
mock(DataSaverController.class),
mock(ManagedProfileController.class),
- mock(ColorDisplayController.class));
+ mock(NightDisplayListener.class));
}
@Test
@@ -66,7 +66,7 @@ public class AutoTileManagerTest extends SysuiTestCase {
if (!ColorDisplayManager.isNightDisplayAvailable(mContext)) {
return;
}
- mAutoTileManager.mColorDisplayCallback.onActivated(true);
+ mAutoTileManager.mNightDisplayCallback.onActivated(true);
verify(mQsTileHost).addTile("night");
}
@@ -75,7 +75,7 @@ public class AutoTileManagerTest extends SysuiTestCase {
if (!ColorDisplayManager.isNightDisplayAvailable(mContext)) {
return;
}
- mAutoTileManager.mColorDisplayCallback.onActivated(false);
+ mAutoTileManager.mNightDisplayCallback.onActivated(false);
verify(mQsTileHost, never()).addTile("night");
}
@@ -84,7 +84,7 @@ public class AutoTileManagerTest extends SysuiTestCase {
if (!ColorDisplayManager.isNightDisplayAvailable(mContext)) {
return;
}
- mAutoTileManager.mColorDisplayCallback.onAutoModeChanged(
+ mAutoTileManager.mNightDisplayCallback.onAutoModeChanged(
ColorDisplayManager.AUTO_MODE_TWILIGHT);
verify(mQsTileHost).addTile("night");
}
@@ -94,7 +94,7 @@ public class AutoTileManagerTest extends SysuiTestCase {
if (!ColorDisplayManager.isNightDisplayAvailable(mContext)) {
return;
}
- mAutoTileManager.mColorDisplayCallback.onAutoModeChanged(
+ mAutoTileManager.mNightDisplayCallback.onAutoModeChanged(
ColorDisplayManager.AUTO_MODE_CUSTOM_TIME);
verify(mQsTileHost).addTile("night");
}
@@ -104,7 +104,7 @@ public class AutoTileManagerTest extends SysuiTestCase {
if (!ColorDisplayManager.isNightDisplayAvailable(mContext)) {
return;
}
- mAutoTileManager.mColorDisplayCallback.onAutoModeChanged(
+ mAutoTileManager.mNightDisplayCallback.onAutoModeChanged(
ColorDisplayManager.AUTO_MODE_DISABLED);
verify(mQsTileHost, never()).addTile("night");
}
diff --git a/packages/overlays/Android.mk b/packages/overlays/Android.mk
index b8a57ae7b98f..1294dbbbfa87 100644
--- a/packages/overlays/Android.mk
+++ b/packages/overlays/Android.mk
@@ -16,17 +16,13 @@ LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := frameworks-base-overlays
-
LOCAL_REQUIRED_MODULES := \
- ExperimentNavigationBarFloatingOverlay \
- ExperimentNavigationBarDefaultOverlay \
- ExperimentNavigationBarSlimOverlay32 \
- ExperimentNavigationBarSlimOverlay40 \
- ExperimentNavigationBarLargeOverlay56 \
- ExperimentNavigationBarLargeOverlay64 \
AccentColorBlackOverlay \
AccentColorGreenOverlay \
AccentColorPurpleOverlay \
+ DisplayCutoutEmulationCornerOverlay \
+ DisplayCutoutEmulationDoubleOverlay \
+ DisplayCutoutEmulationTallOverlay \
FontNotoSerifSourceOverlay \
IconPackCircularAndroidOverlay \
IconPackCircularSettingsOverlay \
@@ -42,7 +38,17 @@ LOCAL_REQUIRED_MODULES := \
IconShapeSquircleOverlay \
IconShapeTeardropOverlay
-
include $(BUILD_PHONY_PACKAGE)
+include $(CLEAR_VARS)
+LOCAL_MODULE := frameworks-base-overlays-debug
+LOCAL_REQUIRED_MODULES := \
+ ExperimentNavigationBarFloatingOverlay \
+ ExperimentNavigationBarDefaultOverlay \
+ ExperimentNavigationBarSlimOverlay32 \
+ ExperimentNavigationBarSlimOverlay40 \
+ ExperimentNavigationBarLargeOverlay56 \
+ ExperimentNavigationBarLargeOverlay64
+
+include $(BUILD_PHONY_PACKAGE)
include $(call first-makefiles-under,$(LOCAL_PATH))
diff --git a/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java b/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
index 8886ee2365c0..1bce11ee95de 100644
--- a/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
+++ b/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
@@ -180,7 +180,7 @@ final class AutofillManagerServiceImpl
mAugmentedAutofillResolver = new FrameworkResourcesServiceNameResolver(master.getContext(),
com.android.internal.R.string.config_defaultAugmentedAutofillService);
mAugmentedAutofillResolver.setOnTemporaryServiceNameChangedCallback(
- (u, s) -> updateRemoteAugmentedAutofillService());
+ (u, s) -> updateRemoteAugmentedAutofillService(s));
updateLocked(disabled);
}
@@ -1048,8 +1048,12 @@ final class AutofillManagerServiceImpl
componentName, mUserId, new RemoteAugmentedAutofillServiceCallbacks() {
@Override
public void onServiceDied(@NonNull RemoteAugmentedAutofillService service) {
- // TODO(b/123100811): properly implement
Slog.w(TAG, "remote augmented autofill service died");
+ final RemoteAugmentedAutofillService remoteService =
+ mRemoteAugmentedAutofillService;
+ if (remoteService != null) {
+ remoteService.destroy();
+ }
}
}, mMaster.isInstantServiceAllowed(), mMaster.verbose);
}
@@ -1060,8 +1064,7 @@ final class AutofillManagerServiceImpl
/**
* Called when the {@link #mAugmentedAutofillResolver} changed (among other places).
*/
- private void updateRemoteAugmentedAutofillService() {
- final String serviceName = mAugmentedAutofillResolver.getServiceName(mUserId);
+ private void updateRemoteAugmentedAutofillService(@Nullable String serviceName) {
if (serviceName == null) {
if (sVerbose) Slog.v(TAG, "updateRemoteAugmentedAutofillService(): time's up!");
if (mRemoteAugmentedAutofillService != null) {
diff --git a/services/autofill/java/com/android/server/autofill/Session.java b/services/autofill/java/com/android/server/autofill/Session.java
index 194332ab8451..04fc2588134e 100644
--- a/services/autofill/java/com/android/server/autofill/Session.java
+++ b/services/autofill/java/com/android/server/autofill/Session.java
@@ -2595,8 +2595,6 @@ final class Session implements RemoteFillService.FillServiceCallbacks, ViewState
final int mode;
if ((supportedModes & FLAG_SMART_SUGGESTION_SYSTEM) != 0) {
mode = FLAG_SMART_SUGGESTION_SYSTEM;
- } else if ((supportedModes & AutofillManager.FLAG_SMART_SUGGESTION_LEGACY) != 0) {
- mode = AutofillManager.FLAG_SMART_SUGGESTION_LEGACY;
} else {
Slog.w(TAG, "Unsupported Smart Suggestion mode: " + supportedModes);
return null;
diff --git a/services/backup/java/com/android/server/backup/encryption/chunking/ByteRange.java b/services/backup/java/com/android/server/backup/encryption/chunking/ByteRange.java
new file mode 100644
index 000000000000..004d9e3b45f1
--- /dev/null
+++ b/services/backup/java/com/android/server/backup/encryption/chunking/ByteRange.java
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import com.android.internal.util.Preconditions;
+
+/** Representation of a range of bytes to be downloaded. */
+final class ByteRange {
+ private final long mStart;
+ private final long mEnd;
+
+ /** Creates a range of bytes which includes {@code mStart} and {@code mEnd}. */
+ ByteRange(long start, long end) {
+ Preconditions.checkArgument(start >= 0);
+ Preconditions.checkArgument(end >= start);
+ mStart = start;
+ mEnd = end;
+ }
+
+ /** Returns the start of the {@code ByteRange}. The start is included in the range. */
+ long getStart() {
+ return mStart;
+ }
+
+ /** Returns the end of the {@code ByteRange}. The end is included in the range. */
+ long getEnd() {
+ return mEnd;
+ }
+
+ /** Returns the number of bytes included in the {@code ByteRange}. */
+ int getLength() {
+ return (int) (mEnd - mStart + 1);
+ }
+
+ /** Creates a new {@link ByteRange} from {@code mStart} to {@code mEnd + length}. */
+ ByteRange extend(long length) {
+ Preconditions.checkArgument(length > 0);
+ return new ByteRange(mStart, mEnd + length);
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) {
+ return true;
+ }
+ if (!(o instanceof ByteRange)) {
+ return false;
+ }
+
+ ByteRange byteRange = (ByteRange) o;
+ return (mEnd == byteRange.mEnd && mStart == byteRange.mStart);
+ }
+
+ @Override
+ public int hashCode() {
+ int result = 17;
+ result = 31 * result + (int) (mStart ^ (mStart >>> 32));
+ result = 31 * result + (int) (mEnd ^ (mEnd >>> 32));
+ return result;
+ }
+
+ @Override
+ public String toString() {
+ return String.format("ByteRange{mStart=%d, mEnd=%d}", mStart, mEnd);
+ }
+}
diff --git a/services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptBackupWriter.java b/services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptBackupWriter.java
new file mode 100644
index 000000000000..69fb5cbf606d
--- /dev/null
+++ b/services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptBackupWriter.java
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import com.android.internal.annotations.VisibleForTesting;
+
+import java.io.IOException;
+import java.io.OutputStream;
+
+/** Writes backup data to a diff script, using a {@link SingleStreamDiffScriptWriter}. */
+public class DiffScriptBackupWriter implements BackupWriter {
+ /**
+ * The maximum size of a chunk in the diff script. The diff script writer {@code mWriter} will
+ * buffer this many bytes in memory.
+ */
+ private static final int ENCRYPTION_DIFF_SCRIPT_MAX_CHUNK_SIZE_BYTES = 1024 * 1024;
+
+ private final SingleStreamDiffScriptWriter mWriter;
+ private long mBytesWritten;
+
+ /**
+ * Constructs a new writer which writes the diff script to the given output stream, using the
+ * maximum new chunk size {@code ENCRYPTION_DIFF_SCRIPT_MAX_CHUNK_SIZE_BYTES}.
+ */
+ public static DiffScriptBackupWriter newInstance(OutputStream outputStream) {
+ SingleStreamDiffScriptWriter writer =
+ new SingleStreamDiffScriptWriter(
+ outputStream, ENCRYPTION_DIFF_SCRIPT_MAX_CHUNK_SIZE_BYTES);
+ return new DiffScriptBackupWriter(writer);
+ }
+
+ @VisibleForTesting
+ DiffScriptBackupWriter(SingleStreamDiffScriptWriter writer) {
+ mWriter = writer;
+ }
+
+ @Override
+ public void writeBytes(byte[] bytes) throws IOException {
+ for (byte b : bytes) {
+ mWriter.writeByte(b);
+ }
+
+ mBytesWritten += bytes.length;
+ }
+
+ @Override
+ public void writeChunk(long start, int length) throws IOException {
+ mWriter.writeChunk(start, length);
+ mBytesWritten += length;
+ }
+
+ @Override
+ public long getBytesWritten() {
+ return mBytesWritten;
+ }
+
+ @Override
+ public void flush() throws IOException {
+ mWriter.flush();
+ }
+}
diff --git a/services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptWriter.java b/services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptWriter.java
new file mode 100644
index 000000000000..49d15712d4cc
--- /dev/null
+++ b/services/backup/java/com/android/server/backup/encryption/chunking/DiffScriptWriter.java
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import java.io.IOException;
+import java.io.OutputStream;
+
+/** Writer that formats a Diff Script and writes it to an output source. */
+interface DiffScriptWriter {
+ /** Adds a new byte to the diff script. */
+ void writeByte(byte b) throws IOException;
+
+ /** Adds a known chunk to the diff script. */
+ void writeChunk(long chunkStart, int chunkLength) throws IOException;
+
+ /** Indicates that no more bytes or chunks will be added to the diff script. */
+ void flush() throws IOException;
+
+ interface Factory {
+ DiffScriptWriter create(OutputStream outputStream);
+ }
+}
diff --git a/services/backup/java/com/android/server/backup/encryption/chunking/OutputStreamWrapper.java b/services/backup/java/com/android/server/backup/encryption/chunking/OutputStreamWrapper.java
new file mode 100644
index 000000000000..4aea60121810
--- /dev/null
+++ b/services/backup/java/com/android/server/backup/encryption/chunking/OutputStreamWrapper.java
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import java.io.OutputStream;
+
+/** An interface that wraps one {@link OutputStream} with another for filtration purposes. */
+public interface OutputStreamWrapper {
+ /** Wraps a given {@link OutputStream}. */
+ OutputStream wrap(OutputStream outputStream);
+}
diff --git a/services/backup/java/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriter.java b/services/backup/java/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriter.java
new file mode 100644
index 000000000000..0e4bd58345d5
--- /dev/null
+++ b/services/backup/java/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriter.java
@@ -0,0 +1,130 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import android.annotation.Nullable;
+
+import com.android.internal.util.Preconditions;
+
+import java.io.IOException;
+import java.io.OutputStream;
+import java.nio.charset.Charset;
+import java.util.Locale;
+
+/**
+ * A {@link DiffScriptWriter} that writes an entire diff script to a single {@link OutputStream}.
+ */
+public class SingleStreamDiffScriptWriter implements DiffScriptWriter {
+ static final byte LINE_SEPARATOR = 0xA;
+ private static final Charset UTF_8 = Charset.forName("UTF-8");
+
+ private final int mMaxNewByteChunkSize;
+ private final OutputStream mOutputStream;
+ private final byte[] mByteBuffer;
+ private int mBufferSize = 0;
+ // Each chunk could be written immediately to the output stream. However,
+ // it is possible that chunks may overlap. We therefore cache the most recent
+ // reusable chunk and try to merge it with future chunks.
+ private ByteRange mReusableChunk;
+
+ public SingleStreamDiffScriptWriter(OutputStream outputStream, int maxNewByteChunkSize) {
+ mOutputStream = outputStream;
+ mMaxNewByteChunkSize = maxNewByteChunkSize;
+ mByteBuffer = new byte[maxNewByteChunkSize];
+ }
+
+ @Override
+ public void writeByte(byte b) throws IOException {
+ if (mReusableChunk != null) {
+ writeReusableChunk();
+ }
+ mByteBuffer[mBufferSize++] = b;
+ if (mBufferSize == mMaxNewByteChunkSize) {
+ writeByteBuffer();
+ }
+ }
+
+ @Override
+ public void writeChunk(long chunkStart, int chunkLength) throws IOException {
+ Preconditions.checkArgument(chunkStart >= 0);
+ Preconditions.checkArgument(chunkLength > 0);
+ if (mBufferSize != 0) {
+ writeByteBuffer();
+ }
+
+ if (mReusableChunk != null && mReusableChunk.getEnd() + 1 == chunkStart) {
+ // The new chunk overlaps the old, so combine them into a single byte range.
+ mReusableChunk = mReusableChunk.extend(chunkLength);
+ } else {
+ writeReusableChunk();
+ mReusableChunk = new ByteRange(chunkStart, chunkStart + chunkLength - 1);
+ }
+ }
+
+ @Override
+ public void flush() throws IOException {
+ Preconditions.checkState(!(mBufferSize != 0 && mReusableChunk != null));
+ if (mBufferSize != 0) {
+ writeByteBuffer();
+ }
+ if (mReusableChunk != null) {
+ writeReusableChunk();
+ }
+ mOutputStream.flush();
+ }
+
+ private void writeByteBuffer() throws IOException {
+ mOutputStream.write(Integer.toString(mBufferSize).getBytes(UTF_8));
+ mOutputStream.write(LINE_SEPARATOR);
+ mOutputStream.write(mByteBuffer, 0, mBufferSize);
+ mOutputStream.write(LINE_SEPARATOR);
+ mBufferSize = 0;
+ }
+
+ private void writeReusableChunk() throws IOException {
+ if (mReusableChunk != null) {
+ mOutputStream.write(
+ String.format(
+ Locale.US,
+ "%d-%d",
+ mReusableChunk.getStart(),
+ mReusableChunk.getEnd())
+ .getBytes(UTF_8));
+ mOutputStream.write(LINE_SEPARATOR);
+ mReusableChunk = null;
+ }
+ }
+
+ /** A factory that creates {@link SingleStreamDiffScriptWriter}s. */
+ public static class Factory implements DiffScriptWriter.Factory {
+ private final int mMaxNewByteChunkSize;
+ private final OutputStreamWrapper mOutputStreamWrapper;
+
+ public Factory(int maxNewByteChunkSize, @Nullable OutputStreamWrapper outputStreamWrapper) {
+ mMaxNewByteChunkSize = maxNewByteChunkSize;
+ mOutputStreamWrapper = outputStreamWrapper;
+ }
+
+ @Override
+ public SingleStreamDiffScriptWriter create(OutputStream outputStream) {
+ if (mOutputStreamWrapper != null) {
+ outputStream = mOutputStreamWrapper.wrap(outputStream);
+ }
+ return new SingleStreamDiffScriptWriter(outputStream, mMaxNewByteChunkSize);
+ }
+ }
+}
diff --git a/services/contentcapture/java/com/android/server/contentcapture/ContentCaptureManagerServiceShellCommand.java b/services/contentcapture/java/com/android/server/contentcapture/ContentCaptureManagerServiceShellCommand.java
index 2f78276bb533..39d5c9d0b777 100644
--- a/services/contentcapture/java/com/android/server/contentcapture/ContentCaptureManagerServiceShellCommand.java
+++ b/services/contentcapture/java/com/android/server/contentcapture/ContentCaptureManagerServiceShellCommand.java
@@ -77,6 +77,15 @@ public final class ContentCaptureManagerServiceShellCommand extends ShellCommand
pw.println(" Temporarily (for DURATION ms) changes the service implemtation.");
pw.println(" To reset, call with just the USER_ID argument.");
pw.println("");
+ pw.println("");
+ pw.println(" set default-service-enabled USER_ID [true|false]");
+ pw.println(" Enable / disable the default service for the user.");
+ pw.println("");
+ pw.println("");
+ pw.println(" get default-service-enabled USER_ID");
+ pw.println(" Checks whether the default service is enabled for the user.");
+ pw.println("");
+ pw.println("");
pw.println(" list sessions [--user USER_ID]");
pw.println(" Lists all pending sessions.");
pw.println("");
@@ -91,6 +100,8 @@ public final class ContentCaptureManagerServiceShellCommand extends ShellCommand
switch(what) {
case "bind-instant-service-allowed":
return getBindInstantService(pw);
+ case "default-service-enabled":
+ return getDefaultServiceEnabled(pw);
default:
pw.println("Invalid set: " + what);
return -1;
@@ -105,6 +116,8 @@ public final class ContentCaptureManagerServiceShellCommand extends ShellCommand
return setBindInstantService(pw);
case "temporary-service":
return setTemporaryService(pw);
+ case "default-service-enabled":
+ return setDefaultServiceEnabled();
default:
pw.println("Invalid set: " + what);
return -1;
@@ -149,6 +162,20 @@ public final class ContentCaptureManagerServiceShellCommand extends ShellCommand
return 0;
}
+ private int setDefaultServiceEnabled() {
+ final int userId = getNextIntArgRequired();
+ final boolean enabled = Boolean.parseBoolean(getNextArg());
+ mService.setDefaultServiceEnabled(userId, enabled);
+ return 0;
+ }
+
+ private int getDefaultServiceEnabled(PrintWriter pw) {
+ final int userId = getNextIntArgRequired();
+ final boolean enabled = mService.isDefaultServiceEnabled(userId);
+ pw.println(enabled);
+ return 0;
+ }
+
private int requestDestroy(PrintWriter pw) {
if (!isNextArgSessions(pw)) {
return -1;
diff --git a/services/core/java/com/android/server/ConnectivityService.java b/services/core/java/com/android/server/ConnectivityService.java
index 80b3d67217fd..fe4411c1dbb5 100644
--- a/services/core/java/com/android/server/ConnectivityService.java
+++ b/services/core/java/com/android/server/ConnectivityService.java
@@ -1833,14 +1833,20 @@ public class ConnectivityService extends IConnectivityManager.Stub
"ConnectivityService");
}
- private void enforceAnyPermissionOf(String... permissions) {
+ private boolean checkAnyPermissionOf(String... permissions) {
for (String permission : permissions) {
if (mContext.checkCallingOrSelfPermission(permission) == PERMISSION_GRANTED) {
- return;
+ return true;
}
}
- throw new SecurityException(
- "Requires one of the following permissions: " + String.join(", ", permissions) + ".");
+ return false;
+ }
+
+ private void enforceAnyPermissionOf(String... permissions) {
+ if (!checkAnyPermissionOf(permissions)) {
+ throw new SecurityException("Requires one of the following permissions: "
+ + String.join(", ", permissions) + ".");
+ }
}
private void enforceInternetPermission() {
@@ -1860,19 +1866,22 @@ public class ConnectivityService extends IConnectivityManager.Stub
}
private void enforceSettingsPermission() {
- mContext.enforceCallingOrSelfPermission(
+ enforceAnyPermissionOf(
android.Manifest.permission.NETWORK_SETTINGS,
- "ConnectivityService");
+ NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
}
private boolean checkSettingsPermission() {
- return PERMISSION_GRANTED == mContext.checkCallingOrSelfPermission(
- android.Manifest.permission.NETWORK_SETTINGS);
+ return checkAnyPermissionOf(
+ android.Manifest.permission.NETWORK_SETTINGS,
+ NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
}
private boolean checkSettingsPermission(int pid, int uid) {
return PERMISSION_GRANTED == mContext.checkPermission(
- android.Manifest.permission.NETWORK_SETTINGS, pid, uid);
+ android.Manifest.permission.NETWORK_SETTINGS, pid, uid)
+ || PERMISSION_GRANTED == mContext.checkPermission(
+ NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, pid, uid);
}
private void enforceTetherAccessPermission() {
@@ -1882,9 +1891,9 @@ public class ConnectivityService extends IConnectivityManager.Stub
}
private void enforceConnectivityInternalPermission() {
- mContext.enforceCallingOrSelfPermission(
+ enforceAnyPermissionOf(
android.Manifest.permission.CONNECTIVITY_INTERNAL,
- "ConnectivityService");
+ NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
}
private void enforceControlAlwaysOnVpnPermission() {
@@ -1895,20 +1904,16 @@ public class ConnectivityService extends IConnectivityManager.Stub
private void enforceNetworkStackSettingsOrSetup() {
enforceAnyPermissionOf(
- android.Manifest.permission.NETWORK_SETTINGS,
- android.Manifest.permission.NETWORK_SETUP_WIZARD,
- android.Manifest.permission.NETWORK_STACK);
- }
-
- private void enforceNetworkStackPermission() {
- mContext.enforceCallingOrSelfPermission(
+ android.Manifest.permission.NETWORK_SETTINGS,
+ android.Manifest.permission.NETWORK_SETUP_WIZARD,
android.Manifest.permission.NETWORK_STACK,
- "ConnectivityService");
+ NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
}
private boolean checkNetworkStackPermission() {
- return PERMISSION_GRANTED == mContext.checkCallingOrSelfPermission(
- android.Manifest.permission.NETWORK_STACK);
+ return checkAnyPermissionOf(
+ android.Manifest.permission.NETWORK_STACK,
+ NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
}
private void enforceConnectivityRestrictedNetworksPermission() {
@@ -3240,6 +3245,25 @@ public class ConnectivityService extends IConnectivityManager.Stub
});
}
+ /**
+ * NetworkStack endpoint to start the captive portal app. The NetworkStack needs to use this
+ * endpoint as it does not have INTERACT_ACROSS_USERS_FULL itself.
+ * @param appExtras Bundle to use as intent extras for the captive portal application.
+ * Must be treated as opaque to avoid preventing the captive portal app to
+ * update its arguments.
+ */
+ @Override
+ public void startCaptivePortalAppInternal(Bundle appExtras) {
+ mContext.checkCallingOrSelfPermission(NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK);
+
+ final Intent appIntent = new Intent(ConnectivityManager.ACTION_CAPTIVE_PORTAL_SIGN_IN);
+ appIntent.putExtras(appExtras);
+ appIntent.setFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT | Intent.FLAG_ACTIVITY_NEW_TASK);
+
+ Binder.withCleanCallingIdentity(() ->
+ mContext.startActivityAsUser(appIntent, UserHandle.CURRENT));
+ }
+
public boolean avoidBadWifi() {
return mMultinetworkPolicyTracker.getAvoidBadWifi();
}
diff --git a/services/core/java/com/android/server/LocationManagerService.java b/services/core/java/com/android/server/LocationManagerService.java
index 5278bbbb4af2..4834ce0da9b3 100644
--- a/services/core/java/com/android/server/LocationManagerService.java
+++ b/services/core/java/com/android/server/LocationManagerService.java
@@ -792,7 +792,7 @@ public class LocationManagerService extends ILocationManager.Stub {
String[] testProviderStrings = resources.getStringArray(
com.android.internal.R.array.config_testLocationProviders);
for (String testProviderString : testProviderStrings) {
- String fragments[] = testProviderString.split(",");
+ String[] fragments = testProviderString.split(",");
String name = fragments[0].trim();
ProviderProperties properties = new ProviderProperties(
Boolean.parseBoolean(fragments[1]) /* requiresNetwork */,
@@ -816,12 +816,6 @@ public class LocationManagerService extends ILocationManager.Stub {
return;
}
- // this call has the side effect of forcing a write to the LOCATION_MODE setting in an OS
- // upgrade case, and ensures that if anyone checks the LOCATION_MODE setting directly, they
- // will see it in an appropriate state (at least after that user becomes foreground for the
- // first time...)
- isLocationEnabledForUser(userId);
-
// let providers know the current user is on the way out before changing the user
for (LocationProvider p : mProviders) {
p.onUserChangingLocked();
@@ -934,17 +928,22 @@ public class LocationManagerService extends ILocationManager.Stub {
@GuardedBy("mLock")
public void dumpLocked(FileDescriptor fd, PrintWriter pw, String[] args) {
- pw.println(mName + " provider:");
+ pw.print(" " + mName + " provider");
if (isMock()) {
- pw.println(" mock=true");
+ pw.print(" [mock]");
}
- pw.println(" attached=" + (mProvider != null));
- if (mIsManagedBySettings) {
- pw.println(" allowed=" + mAllowed);
+ pw.println(":");
+
+ pw.println(" useable=" + mUseable);
+ if (!mUseable) {
+ pw.println(" attached=" + (mProvider != null));
+ if (mIsManagedBySettings) {
+ pw.println(" allowed=" + mAllowed);
+ }
+ pw.println(" enabled=" + mEnabled);
}
- pw.println(" enabled=" + mEnabled);
- pw.println(" useable=" + mUseable);
- pw.println(" properties=" + mProperties);
+
+ pw.println(" properties=" + mProperties);
if (mProvider != null) {
long identity = Binder.clearCallingIdentity();
@@ -1397,14 +1396,10 @@ public class LocationManagerService extends ILocationManager.Stub {
public boolean callStatusChangedLocked(String provider, int status, Bundle extras) {
if (mListener != null) {
try {
- synchronized (this) {
- // synchronize to ensure incrementPendingBroadcastsLocked()
- // is called before decrementPendingBroadcasts()
- mListener.onStatusChanged(provider, status, extras);
- // call this after broadcasting so we do not increment
- // if we throw an exeption.
- incrementPendingBroadcastsLocked();
- }
+ mListener.onStatusChanged(provider, status, extras);
+ // call this after broadcasting so we do not increment
+ // if we throw an exception.
+ incrementPendingBroadcastsLocked();
} catch (RemoteException e) {
return false;
}
@@ -1413,16 +1408,12 @@ public class LocationManagerService extends ILocationManager.Stub {
statusChanged.putExtras(new Bundle(extras));
statusChanged.putExtra(LocationManager.KEY_STATUS_CHANGED, status);
try {
- synchronized (this) {
- // synchronize to ensure incrementPendingBroadcastsLocked()
- // is called before decrementPendingBroadcasts()
- mPendingIntent.send(mContext, 0, statusChanged, this, mHandler,
- getResolutionPermission(mAllowedResolutionLevel),
- PendingIntentUtils.createDontSendToRestrictedAppsBundle(null));
- // call this after broadcasting so we do not increment
- // if we throw an exeption.
- incrementPendingBroadcastsLocked();
- }
+ mPendingIntent.send(mContext, 0, statusChanged, this, mHandler,
+ getResolutionPermission(mAllowedResolutionLevel),
+ PendingIntentUtils.createDontSendToRestrictedAppsBundle(null));
+ // call this after broadcasting so we do not increment
+ // if we throw an exception.
+ incrementPendingBroadcastsLocked();
} catch (PendingIntent.CanceledException e) {
return false;
}
@@ -1433,14 +1424,10 @@ public class LocationManagerService extends ILocationManager.Stub {
public boolean callLocationChangedLocked(Location location) {
if (mListener != null) {
try {
- synchronized (this) {
- // synchronize to ensure incrementPendingBroadcastsLocked()
- // is called before decrementPendingBroadcasts()
- mListener.onLocationChanged(new Location(location));
- // call this after broadcasting so we do not increment
- // if we throw an exeption.
- incrementPendingBroadcastsLocked();
- }
+ mListener.onLocationChanged(new Location(location));
+ // call this after broadcasting so we do not increment
+ // if we throw an exception.
+ incrementPendingBroadcastsLocked();
} catch (RemoteException e) {
return false;
}
@@ -1449,16 +1436,12 @@ public class LocationManagerService extends ILocationManager.Stub {
locationChanged.putExtra(LocationManager.KEY_LOCATION_CHANGED,
new Location(location));
try {
- synchronized (this) {
- // synchronize to ensure incrementPendingBroadcastsLocked()
- // is called before decrementPendingBroadcasts()
- mPendingIntent.send(mContext, 0, locationChanged, this, mHandler,
- getResolutionPermission(mAllowedResolutionLevel),
- PendingIntentUtils.createDontSendToRestrictedAppsBundle(null));
- // call this after broadcasting so we do not increment
- // if we throw an exeption.
- incrementPendingBroadcastsLocked();
- }
+ mPendingIntent.send(mContext, 0, locationChanged, this, mHandler,
+ getResolutionPermission(mAllowedResolutionLevel),
+ PendingIntentUtils.createDontSendToRestrictedAppsBundle(null));
+ // call this after broadcasting so we do not increment
+ // if we throw an exception.
+ incrementPendingBroadcastsLocked();
} catch (PendingIntent.CanceledException e) {
return false;
}
@@ -1473,18 +1456,14 @@ public class LocationManagerService extends ILocationManager.Stub {
if (mListener != null) {
try {
- synchronized (this) {
- // synchronize to ensure incrementPendingBroadcastsLocked()
- // is called before decrementPendingBroadcasts()
- if (enabled) {
- mListener.onProviderEnabled(provider);
- } else {
- mListener.onProviderDisabled(provider);
- }
- // call this after broadcasting so we do not increment
- // if we throw an exeption.
- incrementPendingBroadcastsLocked();
+ if (enabled) {
+ mListener.onProviderEnabled(provider);
+ } else {
+ mListener.onProviderDisabled(provider);
}
+ // call this after broadcasting so we do not increment
+ // if we throw an exception.
+ incrementPendingBroadcastsLocked();
} catch (RemoteException e) {
return false;
}
@@ -1492,16 +1471,12 @@ public class LocationManagerService extends ILocationManager.Stub {
Intent providerIntent = new Intent();
providerIntent.putExtra(LocationManager.KEY_PROVIDER_ENABLED, enabled);
try {
- synchronized (this) {
- // synchronize to ensure incrementPendingBroadcastsLocked()
- // is called before decrementPendingBroadcasts()
- mPendingIntent.send(mContext, 0, providerIntent, this, mHandler,
- getResolutionPermission(mAllowedResolutionLevel),
- PendingIntentUtils.createDontSendToRestrictedAppsBundle(null));
- // call this after broadcasting so we do not increment
- // if we throw an exeption.
- incrementPendingBroadcastsLocked();
- }
+ mPendingIntent.send(mContext, 0, providerIntent, this, mHandler,
+ getResolutionPermission(mAllowedResolutionLevel),
+ PendingIntentUtils.createDontSendToRestrictedAppsBundle(null));
+ // call this after broadcasting so we do not increment
+ // if we throw an exception.
+ incrementPendingBroadcastsLocked();
} catch (PendingIntent.CanceledException e) {
return false;
}
@@ -1515,8 +1490,6 @@ public class LocationManagerService extends ILocationManager.Stub {
synchronized (mLock) {
removeUpdatesLocked(this);
- }
- synchronized (this) {
clearPendingBroadcastsLocked();
}
}
@@ -1524,7 +1497,7 @@ public class LocationManagerService extends ILocationManager.Stub {
@Override
public void onSendFinished(PendingIntent pendingIntent, Intent intent,
int resultCode, String resultData, Bundle resultExtras) {
- synchronized (this) {
+ synchronized (mLock) {
decrementPendingBroadcastsLocked();
}
}
@@ -1533,13 +1506,25 @@ public class LocationManagerService extends ILocationManager.Stub {
// containing the sending of the broadcaset
private void incrementPendingBroadcastsLocked() {
mPendingBroadcasts++;
- mWakeLock.acquire(WAKELOCK_TIMEOUT_MILLIS);
+ // so wakelock calls will succeed
+ long identity = Binder.clearCallingIdentity();
+ try {
+ mWakeLock.acquire(WAKELOCK_TIMEOUT_MILLIS);
+ } finally {
+ Binder.restoreCallingIdentity(identity);
+ }
}
private void decrementPendingBroadcastsLocked() {
if (--mPendingBroadcasts == 0) {
- if (mWakeLock.isHeld()) {
- mWakeLock.release();
+ // so wakelock calls will succeed
+ long identity = Binder.clearCallingIdentity();
+ try {
+ if (mWakeLock.isHeld()) {
+ mWakeLock.release();
+ }
+ } finally {
+ Binder.restoreCallingIdentity(identity);
}
}
}
@@ -1547,8 +1532,14 @@ public class LocationManagerService extends ILocationManager.Stub {
public void clearPendingBroadcastsLocked() {
if (mPendingBroadcasts > 0) {
mPendingBroadcasts = 0;
- if (mWakeLock.isHeld()) {
- mWakeLock.release();
+ // so wakelock calls will succeed
+ long identity = Binder.clearCallingIdentity();
+ try {
+ if (mWakeLock.isHeld()) {
+ mWakeLock.release();
+ }
+ } finally {
+ Binder.restoreCallingIdentity(identity);
}
}
}
@@ -1561,18 +1552,9 @@ public class LocationManagerService extends ILocationManager.Stub {
//LocationListener was removed when it had a pending broadcast and should
//not be added back.
synchronized (mLock) {
- IBinder binder = listener.asBinder();
- Receiver receiver = mReceivers.get(binder);
+ Receiver receiver = mReceivers.get(listener.asBinder());
if (receiver != null) {
- synchronized (receiver) {
- // so wakelock calls will succeed
- long identity = Binder.clearCallingIdentity();
- try {
- receiver.decrementPendingBroadcastsLocked();
- } finally {
- Binder.restoreCallingIdentity(identity);
- }
- }
+ receiver.decrementPendingBroadcastsLocked();
}
}
}
@@ -2072,6 +2054,7 @@ public class LocationManagerService extends ILocationManager.Stub {
if (!provider.isUseableLocked()) {
if (isSettingsExemptLocked(record)) {
providerRequest.forceLocation = true;
+ providerRequest.lowPowerMode = false;
} else {
continue;
}
@@ -2080,7 +2063,9 @@ public class LocationManagerService extends ILocationManager.Stub {
LocationRequest locationRequest = record.mRealRequest;
long interval = locationRequest.getInterval();
- if (!isThrottlingExemptLocked(record.mReceiver.mCallerIdentity)) {
+ // if we're forcing location, don't apply any throttling
+ if (!providerRequest.forceLocation && !isThrottlingExemptLocked(
+ record.mReceiver.mCallerIdentity)) {
if (!record.mIsForegroundUid) {
interval = Math.max(interval, backgroundThrottleInterval);
}
@@ -2174,11 +2159,8 @@ public class LocationManagerService extends ILocationManager.Stub {
return true;
}
- if (isProviderPackage(callerIdentity.mPackageName)) {
- return true;
- }
+ return isProviderPackage(callerIdentity.mPackageName);
- return false;
}
@GuardedBy("mLock")
@@ -2192,11 +2174,8 @@ public class LocationManagerService extends ILocationManager.Stub {
return true;
}
- if (isProviderPackage(record.mReceiver.mCallerIdentity.mPackageName)) {
- return true;
- }
+ return isProviderPackage(record.mReceiver.mCallerIdentity.mPackageName);
- return false;
}
private class UpdateRecord {
@@ -2504,9 +2483,7 @@ public class LocationManagerService extends ILocationManager.Stub {
if (mReceivers.remove(receiver.mKey) != null && receiver.isListener()) {
receiver.getListener().asBinder().unlinkToDeath(receiver, 0);
- synchronized (receiver) {
- receiver.clearPendingBroadcastsLocked();
- }
+ receiver.clearPendingBroadcastsLocked();
}
receiver.updateMonitoring(false);
@@ -2682,7 +2659,6 @@ public class LocationManagerService extends ILocationManager.Stub {
// geo-fence manager uses the public location API, need to clear identity
int uid = Binder.getCallingUid();
- // TODO: http://b/23822629
if (UserHandle.getUserId(uid) != UserHandle.USER_SYSTEM) {
// temporary measure until geofences work for secondary users
Log.w(TAG, "proximity alerts are currently available only to the primary user");
@@ -2723,8 +2699,6 @@ public class LocationManagerService extends ILocationManager.Stub {
return false;
}
- // TODO(b/120449926): The GNSS status listeners should be handled similar to the GNSS
- // measurements listeners.
return mGnssStatusProvider.addListener(callback, new CallerIdentity(Binder.getCallingUid(),
Binder.getCallingPid(), packageName));
}
@@ -2744,7 +2718,6 @@ public class LocationManagerService extends ILocationManager.Stub {
synchronized (mLock) {
CallerIdentity callerIdentity = new CallerIdentity(Binder.getCallingUid(),
Binder.getCallingPid(), packageName);
- // TODO(b/120481270): Register for client death notification and update map.
mGnssMeasurementsListeners.put(listener.asBinder(), callerIdentity);
long identity = Binder.clearCallingIdentity();
try {
@@ -2768,9 +2741,9 @@ public class LocationManagerService extends ILocationManager.Stub {
android.Manifest.permission.LOCATION_HARDWARE,
"Location Hardware permission not granted to inject GNSS measurement corrections.");
if (!hasGnssPermissions(packageName) || mGnssMeasurementsProvider == null) {
- mGnssMeasurementsProvider.injectGnssMeasurementCorrections(measurementCorrections);
- } else {
Slog.e(TAG, "Can not inject GNSS corrections due to no permission.");
+ } else {
+ mGnssMeasurementsProvider.injectGnssMeasurementCorrections(measurementCorrections);
}
}
@@ -2809,7 +2782,6 @@ public class LocationManagerService extends ILocationManager.Stub {
CallerIdentity callerIdentity = new CallerIdentity(Binder.getCallingUid(),
Binder.getCallingPid(), packageName);
- // TODO(b/120481270): Register for client death notification and update map.
mGnssNavigationMessageListeners.put(listener.asBinder(), callerIdentity);
long identity = Binder.clearCallingIdentity();
try {
@@ -3382,7 +3354,9 @@ public class LocationManagerService extends ILocationManager.Stub {
return;
}
pw.println("Current Location Manager state:");
- pw.println(" Location Mode: " + isLocationEnabled());
+ pw.println(" Current user: " + mCurrentUserId + " " + Arrays.toString(
+ mCurrentUserProfiles));
+ pw.println(" Location mode: " + isLocationEnabled());
pw.println(" Location Listeners:");
for (Receiver receiver : mReceivers.values()) {
pw.println(" " + receiver);
@@ -3406,14 +3380,6 @@ public class LocationManagerService extends ILocationManager.Stub {
+ callerIdentity.mPackageName + ": "
+ isThrottlingExemptLocked(callerIdentity));
}
- pw.println(" Overlay Provider Packages:");
- for (LocationProvider provider : mProviders) {
- if (provider.mProvider instanceof LocationProviderProxy) {
- pw.println(" " + provider.getName() + ": "
- + ((LocationProviderProxy) provider.mProvider)
- .getProviderPackages());
- }
- }
pw.println(" Historical Records by Provider:");
for (Map.Entry<PackageProviderKey, PackageStatistics> entry
: mRequestStatistics.statistics.entrySet()) {
diff --git a/services/core/java/com/android/server/am/CoreSettingsObserver.java b/services/core/java/com/android/server/am/CoreSettingsObserver.java
index 360d2960f61a..01946247bd12 100644
--- a/services/core/java/com/android/server/am/CoreSettingsObserver.java
+++ b/services/core/java/com/android/server/am/CoreSettingsObserver.java
@@ -56,6 +56,8 @@ final class CoreSettingsObserver extends ContentObserver {
sGlobalSettingToTypeMap.put(Settings.Global.DEBUG_VIEW_ATTRIBUTES, int.class);
sGlobalSettingToTypeMap.put(
+ Settings.Global.DEBUG_VIEW_ATTRIBUTES_APPLICATION_PACKAGE, String.class);
+ sGlobalSettingToTypeMap.put(
Settings.Global.GLOBAL_SETTINGS_ANGLE_GL_DRIVER_ALL_ANGLE, String.class);
sGlobalSettingToTypeMap.put(
Settings.Global.GLOBAL_SETTINGS_ANGLE_GL_DRIVER_SELECTION_PKGS, String.class);
diff --git a/services/core/java/com/android/server/audio/AudioDeviceBroker.java b/services/core/java/com/android/server/audio/AudioDeviceBroker.java
index a3bae521a162..0dc73d9278a2 100644
--- a/services/core/java/com/android/server/audio/AudioDeviceBroker.java
+++ b/services/core/java/com/android/server/audio/AudioDeviceBroker.java
@@ -381,11 +381,11 @@ import java.util.ArrayList;
//---------------------------------------------------------------------
// Message handling on behalf of helper classes
- /*package*/ void broadcastScoConnectionState(int state) {
+ /*package*/ void postBroadcastScoConnectionState(int state) {
sendIMsgNoDelay(MSG_I_BROADCAST_BT_CONNECTION_STATE, SENDMSG_QUEUE, state);
}
- /*package*/ void broadcastBecomingNoisy() {
+ /*package*/ void postBroadcastBecomingNoisy() {
sendMsgNoDelay(MSG_BROADCAST_AUDIO_BECOMING_NOISY, SENDMSG_REPLACE);
}
@@ -415,6 +415,22 @@ import java.util.ArrayList;
delay);
}
+ /*package*/ void postDisconnectA2dp() {
+ sendMsgNoDelay(MSG_DISCONNECT_A2DP, SENDMSG_QUEUE);
+ }
+
+ /*package*/ void postDisconnectA2dpSink() {
+ sendMsgNoDelay(MSG_DISCONNECT_A2DP_SINK, SENDMSG_QUEUE);
+ }
+
+ /*package*/ void postDisconnectHearingAid() {
+ sendMsgNoDelay(MSG_DISCONNECT_HEARING_AID, SENDMSG_QUEUE);
+ }
+
+ /*package*/ void postDisconnectHeadset() {
+ sendMsgNoDelay(MSG_DISCONNECT_HEADSET, SENDMSG_QUEUE);
+ }
+
//---------------------------------------------------------------------
// Method forwarding between the helper classes (BtHelper, AudioDeviceInventory)
// only call from a "handle"* method or "on"* method
@@ -444,23 +460,6 @@ import java.util.ArrayList;
}
}
- /*package*/ void handleDisconnectA2dp() {
- synchronized (mDeviceStateLock) {
- mDeviceInventory.disconnectA2dp();
- }
- }
- /*package*/ void handleDisconnectA2dpSink() {
- synchronized (mDeviceStateLock) {
- mDeviceInventory.disconnectA2dpSink();
- }
- }
-
- /*package*/ void handleDisconnectHearingAid() {
- synchronized (mDeviceStateLock) {
- mDeviceInventory.disconnectHearingAid();
- }
- }
-
/*package*/ void handleSetA2dpSinkConnectionState(@BluetoothProfile.BtProfileState int state,
@NonNull BtHelper.BluetoothA2dpDeviceInfo btDeviceInfo) {
final int intState = (state == BluetoothA2dp.STATE_CONNECTED)
@@ -482,7 +481,7 @@ import java.util.ArrayList;
state, btDeviceInfo, delay);
}
- /*package*/ void handleSetA2dpSourceConnectionState(@BluetoothProfile.BtProfileState int state,
+ /*package*/ void postSetA2dpSourceConnectionState(@BluetoothProfile.BtProfileState int state,
@NonNull BtHelper.BluetoothA2dpDeviceInfo btDeviceInfo) {
final int intState = (state == BluetoothA2dp.STATE_CONNECTED) ? 1 : 0;
sendILMsgNoDelay(MSG_IL_SET_A2DP_SOURCE_CONNECTION_STATE, SENDMSG_QUEUE, state,
@@ -710,6 +709,26 @@ import java.util.ArrayList;
(BtHelper.BluetoothA2dpDeviceInfo) msg.obj);
}
break;
+ case MSG_DISCONNECT_A2DP:
+ synchronized (mDeviceStateLock) {
+ mDeviceInventory.disconnectA2dp();
+ }
+ break;
+ case MSG_DISCONNECT_A2DP_SINK:
+ synchronized (mDeviceStateLock) {
+ mDeviceInventory.disconnectA2dpSink();
+ }
+ break;
+ case MSG_DISCONNECT_HEARING_AID:
+ synchronized (mDeviceStateLock) {
+ mDeviceInventory.disconnectHearingAid();
+ }
+ break;
+ case MSG_DISCONNECT_HEADSET:
+ synchronized (mDeviceStateLock) {
+ mBtHelper.disconnectHeadset();
+ }
+ break;
default:
Log.wtf(TAG, "Invalid message " + msg.what);
}
@@ -745,6 +764,10 @@ import java.util.ArrayList;
private static final int MSG_I_DISCONNECT_BT_SCO = 16;
private static final int MSG_TOGGLE_HDMI = 17;
private static final int MSG_L_A2DP_ACTIVE_DEVICE_CHANGE = 18;
+ private static final int MSG_DISCONNECT_A2DP = 19;
+ private static final int MSG_DISCONNECT_A2DP_SINK = 20;
+ private static final int MSG_DISCONNECT_HEARING_AID = 21;
+ private static final int MSG_DISCONNECT_HEADSET = 22;
private static boolean isMessageHandledUnderWakelock(int msgId) {
diff --git a/services/core/java/com/android/server/audio/AudioDeviceInventory.java b/services/core/java/com/android/server/audio/AudioDeviceInventory.java
index 11fdc8f05033..37f0496c0db3 100644
--- a/services/core/java/com/android/server/audio/AudioDeviceInventory.java
+++ b/services/core/java/com/android/server/audio/AudioDeviceInventory.java
@@ -859,7 +859,7 @@ public final class AudioDeviceInventory {
// also checks whether media routing if affected by a dynamic policy
if (((device == musicDevice) || mDeviceBroker.isInCommunication())
&& (device == devices) && !mDeviceBroker.hasMediaDynamicPolicy()) {
- mDeviceBroker.broadcastBecomingNoisy();
+ mDeviceBroker.postBroadcastBecomingNoisy();
delay = 1000;
}
diff --git a/services/core/java/com/android/server/audio/AudioService.java b/services/core/java/com/android/server/audio/AudioService.java
index de63d0ef8edf..a6643d49c79f 100644
--- a/services/core/java/com/android/server/audio/AudioService.java
+++ b/services/core/java/com/android/server/audio/AudioService.java
@@ -5120,7 +5120,7 @@ public class AudioService extends IAudioService.Stub
if (mUserSwitchedReceived) {
// attempt to stop music playback for background user except on first user
// switch (i.e. first boot)
- mDeviceBroker.broadcastBecomingNoisy();
+ mDeviceBroker.postBroadcastBecomingNoisy();
}
mUserSwitchedReceived = true;
// the current audio focus owner is no longer valid
diff --git a/services/core/java/com/android/server/audio/BtHelper.java b/services/core/java/com/android/server/audio/BtHelper.java
index b63af8a31cd9..e9189974e988 100644
--- a/services/core/java/com/android/server/audio/BtHelper.java
+++ b/services/core/java/com/android/server/audio/BtHelper.java
@@ -374,10 +374,10 @@ public class BtHelper {
}
/*package*/ synchronized void disconnectAllBluetoothProfiles() {
- mDeviceBroker.handleDisconnectA2dp();
- mDeviceBroker.handleDisconnectA2dpSink();
- disconnectHeadset();
- mDeviceBroker.handleDisconnectHearingAid();
+ mDeviceBroker.postDisconnectA2dp();
+ mDeviceBroker.postDisconnectA2dpSink();
+ mDeviceBroker.postDisconnectHeadset();
+ mDeviceBroker.postDisconnectHearingAid();
}
/*package*/ synchronized void resetBluetoothSco() {
@@ -388,9 +388,14 @@ public class BtHelper {
mDeviceBroker.setBluetoothScoOn(false, "resetBluetoothSco");
}
+ /*package*/ synchronized void disconnectHeadset() {
+ setBtScoActiveDevice(null);
+ mBluetoothHeadset = null;
+ }
+
//----------------------------------------------------------------------
private void broadcastScoConnectionState(int state) {
- mDeviceBroker.broadcastScoConnectionState(state);
+ mDeviceBroker.postBroadcastScoConnectionState(state);
}
private boolean handleBtScoActiveDeviceChange(BluetoothDevice btDevice, boolean isActive) {
@@ -487,7 +492,7 @@ public class BtHelper {
btDevice = deviceList.get(0);
final @BluetoothProfile.BtProfileState int state =
proxy.getConnectionState(btDevice);
- mDeviceBroker.handleSetA2dpSourceConnectionState(
+ mDeviceBroker.postSetA2dpSourceConnectionState(
state, new BluetoothA2dpDeviceInfo(btDevice));
}
break;
@@ -558,19 +563,19 @@ public class BtHelper {
switch (profile) {
case BluetoothProfile.A2DP:
- mDeviceBroker.handleDisconnectA2dp();
+ mDeviceBroker.postDisconnectA2dp();
break;
case BluetoothProfile.A2DP_SINK:
- mDeviceBroker.handleDisconnectA2dpSink();
+ mDeviceBroker.postDisconnectA2dpSink();
break;
case BluetoothProfile.HEADSET:
- disconnectHeadset();
+ mDeviceBroker.postDisconnectHeadset();
break;
case BluetoothProfile.HEARING_AID:
- mDeviceBroker.handleDisconnectHearingAid();
+ mDeviceBroker.postDisconnectHearingAid();
break;
default:
@@ -579,11 +584,6 @@ public class BtHelper {
}
};
- private void disconnectHeadset() {
- setBtScoActiveDevice(null);
- mBluetoothHeadset = null;
- }
-
//----------------------------------------------------------------------
private class ScoClient implements IBinder.DeathRecipient {
private IBinder mCb; // To be notified of client's death
diff --git a/services/core/java/com/android/server/biometrics/face/FaceService.java b/services/core/java/com/android/server/biometrics/face/FaceService.java
index 90342ee31c3e..017503a03816 100644
--- a/services/core/java/com/android/server/biometrics/face/FaceService.java
+++ b/services/core/java/com/android/server/biometrics/face/FaceService.java
@@ -168,6 +168,7 @@ public class FaceService extends BiometricServiceBase {
String opPackageName, int cookie, int callingUid, int callingPid,
int callingUserId) {
checkPermission(USE_BIOMETRIC_INTERNAL);
+ updateActiveGroup(groupId, opPackageName);
final boolean restricted = true; // BiometricPrompt is always restricted
final AuthenticationClientImpl client = new FaceAuthClient(getContext(),
mDaemonWrapper, mHalDeviceId, token,
diff --git a/services/core/java/com/android/server/biometrics/fingerprint/FingerprintService.java b/services/core/java/com/android/server/biometrics/fingerprint/FingerprintService.java
index 62947c7dd8b4..9e0a1c0c2ef2 100644
--- a/services/core/java/com/android/server/biometrics/fingerprint/FingerprintService.java
+++ b/services/core/java/com/android/server/biometrics/fingerprint/FingerprintService.java
@@ -192,6 +192,7 @@ public class FingerprintService extends BiometricServiceBase {
IBiometricServiceReceiverInternal wrapperReceiver, String opPackageName,
int cookie, int callingUid, int callingPid, int callingUserId) {
checkPermission(MANAGE_BIOMETRIC);
+ updateActiveGroup(groupId, opPackageName);
final boolean restricted = true; // BiometricPrompt is always restricted
final AuthenticationClientImpl client = new FingerprintAuthClient(getContext(),
mDaemonWrapper, mHalDeviceId, token,
diff --git a/services/core/java/com/android/server/display/BrightnessTracker.java b/services/core/java/com/android/server/display/BrightnessTracker.java
index 727cf0e9f084..126beeffbb96 100644
--- a/services/core/java/com/android/server/display/BrightnessTracker.java
+++ b/services/core/java/com/android/server/display/BrightnessTracker.java
@@ -34,6 +34,7 @@ import android.hardware.SensorEventListener;
import android.hardware.SensorManager;
import android.hardware.display.AmbientBrightnessDayStats;
import android.hardware.display.BrightnessChangeEvent;
+import android.hardware.display.ColorDisplayManager;
import android.hardware.display.DisplayManager;
import android.hardware.display.DisplayManagerInternal;
import android.hardware.display.DisplayedContentSample;
@@ -57,7 +58,6 @@ import android.view.Display;
import com.android.internal.annotations.GuardedBy;
import com.android.internal.annotations.VisibleForTesting;
-import com.android.internal.app.ColorDisplayController;
import com.android.internal.os.BackgroundThread;
import com.android.internal.util.FastXmlSerializer;
import com.android.internal.util.RingBuffer;
@@ -382,9 +382,8 @@ public class BrightnessTracker {
return;
}
- builder.setNightMode(mInjector.isNightModeActive(mContext, UserHandle.USER_CURRENT));
- builder.setColorTemperature(mInjector.getColorTemperature(mContext,
- UserHandle.USER_CURRENT));
+ builder.setNightMode(mInjector.isNightDisplayActivated(mContext));
+ builder.setColorTemperature(mInjector.getNightDisplayColorTemperature(mContext));
if (mColorSamplingEnabled) {
DisplayedContentSample sample = mInjector.sampleColor(mNoFramesToSample);
@@ -1096,12 +1095,13 @@ public class BrightnessTracker {
return context.getSystemService(PowerManager.class).isInteractive();
}
- public int getColorTemperature(Context context, int userId) {
- return new ColorDisplayController(context, userId).getColorTemperature();
+ public int getNightDisplayColorTemperature(Context context) {
+ return context.getSystemService(ColorDisplayManager.class)
+ .getNightDisplayColorTemperature();
}
- public boolean isNightModeActive(Context context, int userId) {
- return new ColorDisplayController(context, userId).isActivated();
+ public boolean isNightDisplayActivated(Context context) {
+ return context.getSystemService(ColorDisplayManager.class).isNightDisplayActivated();
}
public DisplayedContentSample sampleColor(int noFramesToSample) {
diff --git a/services/core/java/com/android/server/display/ColorDisplayService.java b/services/core/java/com/android/server/display/ColorDisplayService.java
index 0d0ce55c2792..9cb6eeec2126 100644
--- a/services/core/java/com/android/server/display/ColorDisplayService.java
+++ b/services/core/java/com/android/server/display/ColorDisplayService.java
@@ -72,7 +72,6 @@ import android.view.animation.AnimationUtils;
import com.android.internal.R;
import com.android.internal.annotations.VisibleForTesting;
-import com.android.internal.app.ColorDisplayController;
import com.android.internal.util.DumpUtils;
import com.android.server.DisplayThread;
import com.android.server.SystemService;
@@ -115,6 +114,7 @@ public final class ColorDisplayService extends SystemService {
private static final int MSG_APPLY_NIGHT_DISPLAY_IMMEDIATE = 0;
private static final int MSG_APPLY_NIGHT_DISPLAY_ANIMATED = 1;
private static final int MSG_APPLY_GLOBAL_SATURATION = 2;
+ private static final int MSG_APPLY_DISPLAY_WHITE_BALANCE = 3;
/**
* Return value if a setting has not been set.
@@ -447,7 +447,6 @@ public final class ColorDisplayService extends SystemService {
private ContentObserver mUserSetupObserver;
private boolean mBootCompleted;
- private ColorDisplayController mNightDisplayController;
private ContentObserver mContentObserver;
private DisplayWhiteBalanceListener mDisplayWhiteBalanceListener;
@@ -546,8 +545,6 @@ public final class ColorDisplayService extends SystemService {
private void setUp() {
Slog.d(TAG, "setUp: currentUser=" + mCurrentUser);
- mNightDisplayController = new ColorDisplayController(getContext(), mCurrentUser);
-
// Listen for external changes to any of the settings.
if (mContentObserver == null) {
mContentObserver = new ContentObserver(new Handler(DisplayThread.get().getLooper())) {
@@ -585,7 +582,7 @@ public final class ColorDisplayService extends SystemService {
getNightDisplayCustomEndTimeInternal().getLocalTime());
break;
case System.DISPLAY_COLOR_MODE:
- onDisplayColorModeChanged(mNightDisplayController.getColorMode());
+ onDisplayColorModeChanged(getColorModeInternal());
break;
case Secure.ACCESSIBILITY_DISPLAY_INVERSION_ENABLED:
onAccessibilityInversionChanged();
@@ -633,7 +630,7 @@ public final class ColorDisplayService extends SystemService {
// Set the color mode, if valid, and immediately apply the updated tint matrix based on the
// existing activated state. This ensures consistency of tint across the color mode change.
- onDisplayColorModeChanged(mNightDisplayController.getColorMode());
+ onDisplayColorModeChanged(getColorModeInternal());
if (mNightDisplayTintController.isAvailable(getContext())) {
// Reset the activated state.
@@ -666,10 +663,6 @@ public final class ColorDisplayService extends SystemService {
getContext().getContentResolver().unregisterContentObserver(mContentObserver);
- if (mNightDisplayController != null) {
- mNightDisplayController = null;
- }
-
if (mNightDisplayTintController.isAvailable(getContext())) {
if (mNightDisplayAutoMode != null) {
mNightDisplayAutoMode.onStop();
@@ -739,7 +732,7 @@ public final class ColorDisplayService extends SystemService {
}
private void onAccessibilityActivated() {
- onDisplayColorModeChanged(mNightDisplayController.getColorMode());
+ onDisplayColorModeChanged(getColorModeInternal());
}
/**
@@ -870,7 +863,7 @@ public final class ColorDisplayService extends SystemService {
// If disabled, clear the tint. If enabled, do nothing more here and let the next
// temperature update set the correct tint.
if (!activated) {
- applyTint(mDisplayWhiteBalanceTintController, false);
+ mHandler.sendEmptyMessage(MSG_APPLY_DISPLAY_WHITE_BALANCE);
}
}
@@ -1002,8 +995,7 @@ public final class ColorDisplayService extends SystemService {
mCurrentUser);
}
- private @ColorMode
- int getColorModeInternal() {
+ private @ColorMode int getColorModeInternal() {
final ContentResolver cr = getContext().getContentResolver();
if (Secure.getIntForUser(cr, Secure.ACCESSIBILITY_DISPLAY_INVERSION_ENABLED,
0, mCurrentUser) == 1
@@ -1542,7 +1534,7 @@ public final class ColorDisplayService extends SystemService {
mDisplayWhiteBalanceTintController.setMatrix(cct);
if (mDisplayWhiteBalanceTintController.isActivated()) {
- applyTint(mDisplayWhiteBalanceTintController, false);
+ mHandler.sendEmptyMessage(MSG_APPLY_DISPLAY_WHITE_BALANCE);
return true;
}
return false;
@@ -1602,6 +1594,9 @@ public final class ColorDisplayService extends SystemService {
case MSG_APPLY_NIGHT_DISPLAY_ANIMATED:
applyTint(mNightDisplayTintController, false);
break;
+ case MSG_APPLY_DISPLAY_WHITE_BALANCE:
+ applyTint(mDisplayWhiteBalanceTintController, false);
+ break;
}
}
}
diff --git a/services/core/java/com/android/server/display/ColorFade.java b/services/core/java/com/android/server/display/ColorFade.java
index 2f277e4f2ff5..31b497d001eb 100644
--- a/services/core/java/com/android/server/display/ColorFade.java
+++ b/services/core/java/com/android/server/display/ColorFade.java
@@ -636,7 +636,7 @@ final class ColorFade {
mSurfaceLayout = null;
SurfaceControl.openTransaction();
try {
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
mSurface.release();
} finally {
SurfaceControl.closeTransaction();
diff --git a/services/core/java/com/android/server/display/DisplayTransformManager.java b/services/core/java/com/android/server/display/DisplayTransformManager.java
index b1b7d3c8769b..ef92401bf3fd 100644
--- a/services/core/java/com/android/server/display/DisplayTransformManager.java
+++ b/services/core/java/com/android/server/display/DisplayTransformManager.java
@@ -87,7 +87,7 @@ public class DisplayTransformManager {
* Map of level -> color transformation matrix.
*/
@GuardedBy("mColorMatrix")
- private final SparseArray<float[]> mColorMatrix = new SparseArray<>(3);
+ private final SparseArray<float[]> mColorMatrix = new SparseArray<>(5);
/**
* Temporary matrix used internally by {@link #computeColorMatrixLocked()}.
*/
@@ -148,6 +148,21 @@ public class DisplayTransformManager {
}
/**
+ * Sets the current Daltonization mode. This adjusts the color space to correct for or simulate
+ * various types of color blindness.
+ *
+ * @param mode the new Daltonization mode, or -1 to disable
+ */
+ public void setDaltonizerMode(int mode) {
+ synchronized (mDaltonizerModeLock) {
+ if (mDaltonizerMode != mode) {
+ mDaltonizerMode = mode;
+ applyDaltonizerMode(mode);
+ }
+ }
+ }
+
+ /**
* Returns the composition of all current color matrices, or {@code null} if there are none.
*/
@GuardedBy("mColorMatrix")
@@ -167,30 +182,6 @@ public class DisplayTransformManager {
}
/**
- * Returns the current Daltonization mode.
- */
- public int getDaltonizerMode() {
- synchronized (mDaltonizerModeLock) {
- return mDaltonizerMode;
- }
- }
-
- /**
- * Sets the current Daltonization mode. This adjusts the color space to correct for or simulate
- * various types of color blindness.
- *
- * @param mode the new Daltonization mode, or -1 to disable
- */
- public void setDaltonizerMode(int mode) {
- synchronized (mDaltonizerModeLock) {
- if (mDaltonizerMode != mode) {
- mDaltonizerMode = mode;
- applyDaltonizerMode(mode);
- }
- }
- }
-
- /**
* Propagates the provided color transformation matrix to the SurfaceFlinger.
*/
private static void applyColorMatrix(float[] m) {
diff --git a/services/core/java/com/android/server/hdmi/HdmiControlService.java b/services/core/java/com/android/server/hdmi/HdmiControlService.java
index 7376ed2b0679..072238ee7f55 100644
--- a/services/core/java/com/android/server/hdmi/HdmiControlService.java
+++ b/services/core/java/com/android/server/hdmi/HdmiControlService.java
@@ -2412,7 +2412,8 @@ public class HdmiControlService extends SystemService {
void wakeUp() {
assertRunOnServiceThread();
mWakeUpMessageReceived = true;
- mPowerManager.wakeUp(SystemClock.uptimeMillis(), "android.server.hdmi:WAKE");
+ mPowerManager.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_HDMI,
+ "android.server.hdmi:WAKE");
// PowerManger will send the broadcast Intent.ACTION_SCREEN_ON and after this gets
// the intent, the sequence will continue at onWakeUp().
}
@@ -2637,7 +2638,8 @@ public class HdmiControlService extends SystemService {
playback().sendStandby(0 /* unused */);
}
} else if (isPowerStandbyOrTransient() && !isStandbyModeOn) {
- mPowerManager.wakeUp(SystemClock.uptimeMillis(), "android.server.hdmi:WAKE");
+ mPowerManager.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_HDMI,
+ "android.server.hdmi:WAKE");
if (playback() != null) {
oneTouchPlay(new IHdmiControlCallback.Stub() {
@Override
diff --git a/services/core/java/com/android/server/infra/AbstractMasterSystemService.java b/services/core/java/com/android/server/infra/AbstractMasterSystemService.java
index 532aa01f4438..2bfb31f6e74f 100644
--- a/services/core/java/com/android/server/infra/AbstractMasterSystemService.java
+++ b/services/core/java/com/android/server/infra/AbstractMasterSystemService.java
@@ -286,6 +286,46 @@ public abstract class AbstractMasterSystemService<M extends AbstractMasterSystem
}
/**
+ * Sets whether the default service should be used.
+ *
+ * <p>Typically used during CTS tests to make sure only the default service doesn't interfere
+ * with the test results.
+ *
+ * @throws SecurityException if caller is not allowed to manage this service's settings.
+ */
+ public final void setDefaultServiceEnabled(@UserIdInt int userId, boolean enabled) {
+ Slog.i(mTag, "setDefaultServiceEnabled() for userId " + userId + ": " + enabled);
+ enforceCallingPermissionForManagement();
+
+ synchronized (mLock) {
+ final S oldService = peekServiceForUserLocked(userId);
+ if (oldService != null) {
+ oldService.removeSelfFromCacheLocked();
+ }
+ mServiceNameResolver.setDefaultServiceEnabled(userId, enabled);
+
+ // Must update the service on cache so its initialization code is triggered
+ updateCachedServiceLocked(userId);
+ }
+ }
+
+ /**
+ * Checks whether the default service should be used.
+ *
+ * <p>Typically used during CTS tests to make sure only the default service doesn't interfere
+ * with the test results.
+ *
+ * @throws SecurityException if caller is not allowed to manage this service's settings.
+ */
+ public final boolean isDefaultServiceEnabled(@UserIdInt int userId) {
+ enforceCallingPermissionForManagement();
+
+ synchronized (mLock) {
+ return mServiceNameResolver.isDefaultServiceEnabled(userId);
+ }
+ }
+
+ /**
* Gets the maximum time the service implementation can be changed.
*
* @throws UnsupportedOperationException if subclass doesn't override it.
diff --git a/services/core/java/com/android/server/infra/FrameworkResourcesServiceNameResolver.java b/services/core/java/com/android/server/infra/FrameworkResourcesServiceNameResolver.java
index 7f198acfd743..cf84e22e7dd1 100644
--- a/services/core/java/com/android/server/infra/FrameworkResourcesServiceNameResolver.java
+++ b/services/core/java/com/android/server/infra/FrameworkResourcesServiceNameResolver.java
@@ -27,6 +27,7 @@ import android.os.SystemClock;
import android.text.TextUtils;
import android.util.Slog;
import android.util.SparseArray;
+import android.util.SparseBooleanArray;
import android.util.TimeUtils;
import com.android.internal.annotations.GuardedBy;
@@ -61,6 +62,15 @@ public final class FrameworkResourcesServiceNameResolver implements ServiceNameR
private final SparseArray<String> mTemporaryServiceNames = new SparseArray<>();
/**
+ * Map of default services that have been disabled by
+ * {@link #setDefaultServiceEnabled(int, boolean)},keyed by {@code userId}.
+ *
+ * <p>Typically used by Shell command and/or CTS tests.
+ */
+ @GuardedBy("mLock")
+ private final SparseBooleanArray mDefaultServicesDisabled = new SparseBooleanArray();
+
+ /**
* When the temporary service will expire (and reset back to the default).
*/
@GuardedBy("mLock")
@@ -99,12 +109,18 @@ public final class FrameworkResourcesServiceNameResolver implements ServiceNameR
final String temporaryName = mTemporaryServiceNames.get(userId);
if (temporaryName != null) {
// Always log it, as it should only be used on CTS or during development
- Slog.w(TAG, "getComponentName(): using temporary name " + temporaryName
+ Slog.w(TAG, "getServiceName(): using temporary name " + temporaryName
+ " for user " + userId);
return temporaryName;
- } else {
- return getDefaultServiceName(userId);
}
+ final boolean disabled = mDefaultServicesDisabled.get(userId);
+ if (disabled) {
+ // Always log it, as it should only be used on CTS or during development
+ Slog.w(TAG, "getServiceName(): temporary name not set and default disabled for "
+ + "user " + userId);
+ return null;
+ }
+ return getDefaultServiceName(userId);
}
}
@@ -158,6 +174,24 @@ public final class FrameworkResourcesServiceNameResolver implements ServiceNameR
}
@Override
+ public void setDefaultServiceEnabled(int userId, boolean enabled) {
+ synchronized (mLock) {
+ if (enabled) {
+ mDefaultServicesDisabled.removeAt(userId);
+ } else {
+ mDefaultServicesDisabled.put(userId, true);
+ }
+ }
+ }
+
+ @Override
+ public boolean isDefaultServiceEnabled(int userId) {
+ synchronized (mLock) {
+ return mDefaultServicesDisabled.get(userId);
+ }
+ }
+
+ @Override
public String toString() {
return "FrameworkResourcesServiceNamer[temps=" + mTemporaryServiceNames + "]";
}
@@ -168,6 +202,7 @@ public final class FrameworkResourcesServiceNameResolver implements ServiceNameR
synchronized (mLock) {
pw.print("FrameworkResourcesServiceNamer: resId="); pw.print(mResourceId);
pw.print(", numberTemps="); pw.print(mTemporaryServiceNames.size());
+ pw.print(", enabledDefaults="); pw.print(mDefaultServicesDisabled.size());
}
}
@@ -181,7 +216,9 @@ public final class FrameworkResourcesServiceNameResolver implements ServiceNameR
final long ttl = mTemporaryServiceExpiration - SystemClock.elapsedRealtime();
pw.print(" (expires in "); TimeUtils.formatDuration(ttl, pw); pw.print("), ");
}
- pw.print("defaultName="); pw.println(getDefaultServiceName(userId));
+ pw.print("defaultName="); pw.print(getDefaultServiceName(userId));
+ final boolean disabled = mDefaultServicesDisabled.get(userId);
+ pw.println(disabled ? " (disabled)" : " (enabled)");
}
}
diff --git a/services/core/java/com/android/server/infra/ServiceNameResolver.java b/services/core/java/com/android/server/infra/ServiceNameResolver.java
index bc11ff302ca9..5b60413eefad 100644
--- a/services/core/java/com/android/server/infra/ServiceNameResolver.java
+++ b/services/core/java/com/android/server/infra/ServiceNameResolver.java
@@ -108,6 +108,36 @@ public interface ServiceNameResolver {
}
/**
+ * Sets whether the default service should be used when the temporary service is not set.
+ *
+ * <p>Typically used during CTS tests to make sure only the default service doesn't interfere
+ * with the test results.
+ *
+ * @param userId user handle
+ * @param enabled whether the default service should be used when the temporary service is not
+ * set
+ *
+ * @throws UnsupportedOperationException if not implemented.
+ */
+ default void setDefaultServiceEnabled(@UserIdInt int userId, boolean enabled) {
+ throw new UnsupportedOperationException("changing default service not supported");
+ }
+
+ /**
+ * Checks whether the default service should be used when the temporary service is not set.
+ *
+ * <p>Typically used during CTS tests to make sure only the default service doesn't interfere
+ * with the test results.
+ *
+ * @param userId user handle
+ *
+ * @throws UnsupportedOperationException if not implemented.
+ */
+ default boolean isDefaultServiceEnabled(@UserIdInt int userId) {
+ throw new UnsupportedOperationException("checking default service not supported");
+ }
+
+ /**
* Dumps the generic info in just one line (without calling {@code println}.
*/
// TODO(b/117779333): support proto
diff --git a/services/core/java/com/android/server/location/LocationProviderProxy.java b/services/core/java/com/android/server/location/LocationProviderProxy.java
index 34c8786b00b3..afe34737fdee 100644
--- a/services/core/java/com/android/server/location/LocationProviderProxy.java
+++ b/services/core/java/com/android/server/location/LocationProviderProxy.java
@@ -183,12 +183,17 @@ public class LocationProviderProxy extends AbstractLocationProvider {
@Override
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
- pw.println(" service=" + mServiceWatcher);
+ pw.println(" service=" + mServiceWatcher);
+ synchronized (mProviderPackagesLock) {
+ if (mProviderPackages.size() > 1) {
+ pw.println(" additional packages=" + mProviderPackages);
+ }
+ }
mServiceWatcher.runOnBinderBlocking(binder -> {
try {
TransferPipe.dumpAsync(binder, fd, args);
} catch (IOException | RemoteException e) {
- pw.println(" failed to dump location provider");
+ pw.println(" <failed to dump location provider: " + e + ">");
}
return null;
}, null);
diff --git a/services/core/java/com/android/server/pm/PackageInstallerSession.java b/services/core/java/com/android/server/pm/PackageInstallerSession.java
index d06fc513c0e8..1b719048bc89 100644
--- a/services/core/java/com/android/server/pm/PackageInstallerSession.java
+++ b/services/core/java/com/android/server/pm/PackageInstallerSession.java
@@ -44,7 +44,6 @@ import static com.android.server.pm.PackageInstallerService.prepareStageDir;
import android.Manifest;
import android.annotation.NonNull;
import android.annotation.Nullable;
-import android.apex.IApexService;
import android.app.admin.DevicePolicyManagerInternal;
import android.content.Context;
import android.content.IIntentReceiver;
@@ -80,7 +79,6 @@ import android.os.ParcelableException;
import android.os.Process;
import android.os.RemoteException;
import android.os.RevocableFileDescriptor;
-import android.os.ServiceManager;
import android.os.SystemProperties;
import android.os.UserHandle;
import android.os.storage.StorageManager;
@@ -1084,6 +1082,11 @@ public class PackageInstallerSession extends IPackageInstallerSession.Stub {
dispatchSessionFinished(PackageManager.INSTALL_SUCCEEDED, "Session staged", null);
return;
}
+ if ((params.installFlags & PackageManager.INSTALL_APEX) != 0) {
+ throw new PackageManagerException(
+ PackageManager.INSTALL_FAILED_INTERNAL_ERROR,
+ "APEX packages can only be installed using staged sessions.");
+ }
final PackageManagerService.ActiveInstallSession committingSession =
makeSessionActiveLocked();
if (committingSession == null) {
@@ -1101,12 +1104,6 @@ public class PackageInstallerSession extends IPackageInstallerSession.Stub {
final PackageManagerService.ActiveInstallSession activeSession =
session.makeSessionActiveLocked();
if (activeSession != null) {
- if ((activeSession.getSessionParams().installFlags
- & PackageManager.INSTALL_APEX) != 0) {
- throw new PackageManagerException(
- PackageManager.INSTALL_FAILED_INTERNAL_ERROR,
- "Atomic install is not supported for APEX packages.");
- }
childSessions.add(activeSession);
}
} catch (PackageManagerException e) {
@@ -1124,27 +1121,7 @@ public class PackageInstallerSession extends IPackageInstallerSession.Stub {
}
mPm.installStage(childSessions);
} else {
- if ((params.installFlags & PackageManager.INSTALL_APEX) != 0) {
- commitApexLocked();
- } else {
- mPm.installStage(committingSession);
- }
- }
- }
-
- @GuardedBy("mLock")
- private void commitApexLocked() throws PackageManagerException {
- try {
- IApexService apex = IApexService.Stub.asInterface(
- ServiceManager.getService("apexservice"));
- apex.stagePackage(mResolvedBaseFile.toString());
- } catch (Throwable e) {
- // Convert all exceptions into package manager exceptions as only those are handled
- // in the code above
- throw new PackageManagerException(e);
- } finally {
- destroyInternal();
- dispatchSessionFinished(PackageManager.INSTALL_SUCCEEDED, "APEX installed", null);
+ mPm.installStage(committingSession);
}
}
diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java
index 32dc98837854..eaedec597359 100644
--- a/services/core/java/com/android/server/pm/PackageManagerService.java
+++ b/services/core/java/com/android/server/pm/PackageManagerService.java
@@ -195,7 +195,6 @@ import android.content.pm.SharedLibraryInfo;
import android.content.pm.Signature;
import android.content.pm.SuspendDialogInfo;
import android.content.pm.UserInfo;
-import android.content.pm.UsesPermissionInfo;
import android.content.pm.VerifierDeviceIdentity;
import android.content.pm.VerifierInfo;
import android.content.pm.VersionedPackage;
@@ -11313,26 +11312,6 @@ public class PackageManagerService extends IPackageManager.Stub
}
}
}
-
- // Check permission usage info requirements.
- if (pkg.applicationInfo.targetSdkVersion >= Build.VERSION_CODES.Q) {
- for (UsesPermissionInfo upi : pkg.usesPermissionInfos) {
- if (!mPermissionManager.isPermissionUsageInfoRequired(upi.getPermission())) {
- continue;
- }
- if (upi.getDataSentOffDevice() == UsesPermissionInfo.USAGE_UNDEFINED
- || upi.getDataSharedWithThirdParty()
- == UsesPermissionInfo.USAGE_UNDEFINED
- || upi.getDataUsedForMonetization()
- == UsesPermissionInfo.USAGE_UNDEFINED
- || upi.getDataRetention() == UsesPermissionInfo.RETENTION_UNDEFINED) {
- // STOPSHIP: Make this throw
- Slog.e(TAG, "Package " + pkg.packageName + " does not provide usage "
- + "information for permission " + upi.getPermission()
- + ". This will be a fatal error in Q.");
- }
- }
- }
}
}
diff --git a/services/core/java/com/android/server/pm/dex/DexManager.java b/services/core/java/com/android/server/pm/dex/DexManager.java
index 2213901b2049..ee6995b11430 100644
--- a/services/core/java/com/android/server/pm/dex/DexManager.java
+++ b/services/core/java/com/android/server/pm/dex/DexManager.java
@@ -228,8 +228,11 @@ public class DexManager {
continue;
}
- mDexLogger.recordDex(loaderUserId, dexPath, searchResult.mOwningPackageName,
- loadingAppInfo.packageName);
+ if (!primaryOrSplit) {
+ // Record loading of a DEX file from an app data directory.
+ mDexLogger.recordDex(loaderUserId, dexPath, searchResult.mOwningPackageName,
+ loadingAppInfo.packageName);
+ }
if (classLoaderContexts != null) {
diff --git a/services/core/java/com/android/server/pm/permission/BasePermission.java b/services/core/java/com/android/server/pm/permission/BasePermission.java
index 173d9a0551df..1957eb89fd0c 100644
--- a/services/core/java/com/android/server/pm/permission/BasePermission.java
+++ b/services/core/java/com/android/server/pm/permission/BasePermission.java
@@ -105,8 +105,6 @@ public final class BasePermission {
*/
private boolean perUser;
- boolean usageInfoRequired;
-
public BasePermission(String _name, String _sourcePackageName, @PermissionType int _type) {
name = _name;
sourcePackageName = _sourcePackageName;
@@ -375,7 +373,6 @@ public final class BasePermission {
}
if (bp.perm == p) {
bp.protectionLevel = p.info.protectionLevel;
- bp.usageInfoRequired = p.info.usageInfoRequired;
}
if (PackageManagerService.DEBUG_PACKAGE_SCANNING && r != null) {
Log.d(TAG, " Permissions: " + r);
@@ -455,7 +452,6 @@ public final class BasePermission {
permissionInfo.packageName = sourcePackageName;
permissionInfo.nonLocalizedLabel = name;
permissionInfo.protectionLevel = protectionLevel;
- permissionInfo.usageInfoRequired = usageInfoRequired;
return permissionInfo;
}
@@ -484,7 +480,6 @@ public final class BasePermission {
bp.protectionLevel = readInt(parser, null, "protection",
PermissionInfo.PROTECTION_NORMAL);
bp.protectionLevel = PermissionInfo.fixProtectionLevel(bp.protectionLevel);
- bp.usageInfoRequired = readInt(parser, null, "usageInfoRequired", 0) != 0;
if (dynamic) {
final PermissionInfo pi = new PermissionInfo();
pi.packageName = sourcePackage.intern();
@@ -492,7 +487,6 @@ public final class BasePermission {
pi.icon = readInt(parser, null, "icon", 0);
pi.nonLocalizedLabel = parser.getAttributeValue(null, "label");
pi.protectionLevel = bp.protectionLevel;
- pi.usageInfoRequired = bp.usageInfoRequired;
bp.pendingPermissionInfo = pi;
}
out.put(bp.name, bp);
@@ -525,7 +519,6 @@ public final class BasePermission {
if (protectionLevel != PermissionInfo.PROTECTION_NORMAL) {
serializer.attribute(null, "protection", Integer.toString(protectionLevel));
}
- serializer.attribute(null, "usageInfoRequired", usageInfoRequired ? "1" : "0");
if (type == BasePermission.TYPE_DYNAMIC) {
final PermissionInfo pi = perm != null ? perm.info : pendingPermissionInfo;
if (pi != null) {
@@ -562,7 +555,6 @@ public final class BasePermission {
if (!compareStrings(pi1.nonLocalizedLabel, pi2.nonLocalizedLabel)) return false;
// We'll take care of setting this one.
if (!compareStrings(pi1.packageName, pi2.packageName)) return false;
- if (pi1.usageInfoRequired != pi2.usageInfoRequired) return false;
// These are not currently stored in settings.
//if (!compareStrings(pi1.group, pi2.group)) return false;
//if (!compareStrings(pi1.nonLocalizedDescription, pi2.nonLocalizedDescription)) return false;
@@ -610,8 +602,6 @@ public final class BasePermission {
pw.print(" enforced=");
pw.println(readEnforced);
}
- pw.print(" usageInfoRequired=");
- pw.println(usageInfoRequired);
return true;
}
}
diff --git a/services/core/java/com/android/server/pm/permission/PermissionManagerInternal.java b/services/core/java/com/android/server/pm/permission/PermissionManagerInternal.java
index 189d0f476a8c..f4979746bae3 100644
--- a/services/core/java/com/android/server/pm/permission/PermissionManagerInternal.java
+++ b/services/core/java/com/android/server/pm/permission/PermissionManagerInternal.java
@@ -181,9 +181,4 @@ public abstract class PermissionManagerInternal {
/** HACK HACK methods to allow for partial migration of data to the PermissionManager class */
public abstract @Nullable BasePermission getPermissionTEMP(@NonNull String permName);
-
- /**
- * Returns {@code true} if {@code permName} has {@code usageInfoRequired} set.
- */
- public abstract boolean isPermissionUsageInfoRequired(@NonNull String permName);
}
diff --git a/services/core/java/com/android/server/pm/permission/PermissionManagerService.java b/services/core/java/com/android/server/pm/permission/PermissionManagerService.java
index a4413f963642..38940d6241a6 100644
--- a/services/core/java/com/android/server/pm/permission/PermissionManagerService.java
+++ b/services/core/java/com/android/server/pm/permission/PermissionManagerService.java
@@ -2737,12 +2737,5 @@ public class PermissionManagerService {
return mSettings.getPermissionLocked(permName);
}
}
- @Override
- public boolean isPermissionUsageInfoRequired(String permName) {
- synchronized (PermissionManagerService.this.mLock) {
- BasePermission bp = mSettings.getPermissionLocked(permName);
- return bp != null && bp.usageInfoRequired;
- }
- }
}
}
diff --git a/services/core/java/com/android/server/policy/PhoneWindowManager.java b/services/core/java/com/android/server/policy/PhoneWindowManager.java
index 0796a9c896a3..b00193f5453f 100644
--- a/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -148,6 +148,7 @@ import android.os.IBinder;
import android.os.IDeviceIdleController;
import android.os.Message;
import android.os.PowerManager;
+import android.os.PowerManager.WakeReason;
import android.os.PowerManagerInternal;
import android.os.Process;
import android.os.RemoteException;
@@ -189,6 +190,7 @@ import android.view.ViewConfiguration;
import android.view.WindowManager;
import android.view.WindowManager.LayoutParams;
import android.view.WindowManagerGlobal;
+import android.view.WindowManagerPolicyConstants;
import android.view.accessibility.AccessibilityEvent;
import android.view.accessibility.AccessibilityManager;
import android.view.animation.Animation;
@@ -809,7 +811,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
performHapticFeedbackLw(null, HapticFeedbackConstants.VIRTUAL_KEY, false,
"Wake Up");
wakeUp(SystemClock.uptimeMillis(), mAllowTheaterModeWakeFromWakeGesture,
- "android.policy:GESTURE");
+ PowerManager.WAKE_REASON_GESTURE, "android.policy:GESTURE");
}
}
}
@@ -3527,7 +3529,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
if (lidOpen) {
wakeUp(SystemClock.uptimeMillis(), mAllowTheaterModeWakeFromLidSwitch,
- "android.policy:LID");
+ PowerManager.WAKE_REASON_LID, "android.policy:LID");
} else if (!mLidControlsSleep) {
mPowerManager.userActivity(SystemClock.uptimeMillis(), false);
}
@@ -3550,7 +3552,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
intent = new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA);
}
wakeUp(whenNanos / 1000000, mAllowTheaterModeWakeFromCameraLens,
- "android.policy:CAMERA_COVER");
+ PowerManager.WAKE_REASON_CAMERA_LAUNCH, "android.policy:CAMERA_COVER");
startActivityAsUser(intent, UserHandle.CURRENT_OR_SELF);
}
mCameraLensCoverState = lensCoverState;
@@ -3679,7 +3681,8 @@ public class PhoneWindowManager implements WindowManagerPolicy {
if (isValidGlobalKey(keyCode)
&& mGlobalKeyManager.shouldHandleGlobalKey(keyCode, event)) {
if (isWakeKey) {
- wakeUp(event.getEventTime(), mAllowTheaterModeWakeFromKey, "android.policy:KEY");
+ wakeUp(event.getEventTime(), mAllowTheaterModeWakeFromKey,
+ PowerManager.WAKE_REASON_WAKE_KEY, "android.policy:KEY");
}
return result;
}
@@ -4025,7 +4028,8 @@ public class PhoneWindowManager implements WindowManagerPolicy {
}
if (isWakeKey) {
- wakeUp(event.getEventTime(), mAllowTheaterModeWakeFromKey, "android.policy:KEY");
+ wakeUp(event.getEventTime(), mAllowTheaterModeWakeFromKey,
+ PowerManager.WAKE_REASON_WAKE_KEY, "android.policy:KEY");
}
return result;
@@ -4125,7 +4129,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
public int interceptMotionBeforeQueueingNonInteractive(long whenNanos, int policyFlags) {
if ((policyFlags & FLAG_WAKE) != 0) {
if (wakeUp(whenNanos / 1000000, mAllowTheaterModeWakeFromMotion,
- "android.policy:MOTION")) {
+ PowerManager.WAKE_REASON_WAKE_MOTION, "android.policy:MOTION")) {
return 0;
}
}
@@ -4139,7 +4143,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
// wake up in this case.
if (isTheaterModeEnabled() && (policyFlags & FLAG_WAKE) != 0) {
wakeUp(whenNanos / 1000000, mAllowTheaterModeWakeFromMotionWhenNotDreaming,
- "android.policy:MOTION");
+ PowerManager.WAKE_REASON_WAKE_MOTION, "android.policy:MOTION");
}
return 0;
@@ -4371,7 +4375,10 @@ public class PhoneWindowManager implements WindowManagerPolicy {
// Called on the PowerManager's Notifier thread.
@Override
public void startedGoingToSleep(int why) {
- if (DEBUG_WAKEUP) Slog.i(TAG, "Started going to sleep... (why=" + why + ")");
+ if (DEBUG_WAKEUP) {
+ Slog.i(TAG, "Started going to sleep... (why="
+ + WindowManagerPolicyConstants.offReasonToString(why) + ")");
+ }
mGoingToSleep = true;
mRequestedOrGoingToSleep = true;
@@ -4385,7 +4392,10 @@ public class PhoneWindowManager implements WindowManagerPolicy {
@Override
public void finishedGoingToSleep(int why) {
EventLog.writeEvent(70000, 0);
- if (DEBUG_WAKEUP) Slog.i(TAG, "Finished going to sleep... (why=" + why + ")");
+ if (DEBUG_WAKEUP) {
+ Slog.i(TAG, "Finished going to sleep... (why="
+ + WindowManagerPolicyConstants.offReasonToString(why) + ")");
+ }
MetricsLogger.histogram(mContext, "screen_timeout", mLockScreenTimeout / 1000);
mGoingToSleep = false;
@@ -4409,9 +4419,12 @@ public class PhoneWindowManager implements WindowManagerPolicy {
// Called on the PowerManager's Notifier thread.
@Override
- public void startedWakingUp() {
+ public void startedWakingUp(@OnReason int why) {
EventLog.writeEvent(70000, 1);
- if (DEBUG_WAKEUP) Slog.i(TAG, "Started waking up...");
+ if (DEBUG_WAKEUP) {
+ Slog.i(TAG, "Started waking up... (why="
+ + WindowManagerPolicyConstants.onReasonToString(why) + ")");
+ }
mDefaultDisplayPolicy.setAwake(true);
@@ -4432,8 +4445,11 @@ public class PhoneWindowManager implements WindowManagerPolicy {
// Called on the PowerManager's Notifier thread.
@Override
- public void finishedWakingUp() {
- if (DEBUG_WAKEUP) Slog.i(TAG, "Finished waking up...");
+ public void finishedWakingUp(@OnReason int why) {
+ if (DEBUG_WAKEUP) {
+ Slog.i(TAG, "Finished waking up... (why="
+ + WindowManagerPolicyConstants.onReasonToString(why) + ")");
+ }
if (mKeyguardDelegate != null) {
mKeyguardDelegate.onFinishedWakingUp();
@@ -4441,10 +4457,12 @@ public class PhoneWindowManager implements WindowManagerPolicy {
}
private void wakeUpFromPowerKey(long eventTime) {
- wakeUp(eventTime, mAllowTheaterModeWakeFromPowerKey, "android.policy:POWER");
+ wakeUp(eventTime, mAllowTheaterModeWakeFromPowerKey,
+ PowerManager.WAKE_REASON_POWER_BUTTON, "android.policy:POWER");
}
- private boolean wakeUp(long wakeTime, boolean wakeInTheaterMode, String reason) {
+ private boolean wakeUp(long wakeTime, boolean wakeInTheaterMode, @WakeReason int reason,
+ String details) {
final boolean theaterModeEnabled = isTheaterModeEnabled();
if (!wakeInTheaterMode && theaterModeEnabled) {
return false;
@@ -4455,7 +4473,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
Settings.Global.THEATER_MODE_ON, 0);
}
- mPowerManager.wakeUp(wakeTime, reason);
+ mPowerManager.wakeUp(wakeTime, reason, details);
return true;
}
@@ -4786,7 +4804,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
mKeyguardDelegate.onBootCompleted();
}
}
- startedWakingUp();
+ startedWakingUp(ON_BECAUSE_OF_UNKNOWN);
screenTurningOn(null);
screenTurnedOn();
}
diff --git a/services/core/java/com/android/server/policy/WindowManagerPolicy.java b/services/core/java/com/android/server/policy/WindowManagerPolicy.java
index e18cd179b113..d1bd102f11dc 100644
--- a/services/core/java/com/android/server/policy/WindowManagerPolicy.java
+++ b/services/core/java/com/android/server/policy/WindowManagerPolicy.java
@@ -1070,12 +1070,12 @@ public interface WindowManagerPolicy extends WindowManagerPolicyConstants {
/**
* Called when the device has started waking up.
*/
- public void startedWakingUp();
+ void startedWakingUp(@OnReason int reason);
/**
* Called when the device has finished waking up.
*/
- public void finishedWakingUp();
+ void finishedWakingUp(@OnReason int reason);
/**
* Called when the device has started going to sleep.
diff --git a/services/core/java/com/android/server/power/Notifier.java b/services/core/java/com/android/server/power/Notifier.java
index c3f20aab568e..1a82858147f4 100644
--- a/services/core/java/com/android/server/power/Notifier.java
+++ b/services/core/java/com/android/server/power/Notifier.java
@@ -36,6 +36,7 @@ import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.os.PowerManager;
+import android.os.PowerManager.WakeReason;
import android.os.PowerManagerInternal;
import android.os.Process;
import android.os.RemoteException;
@@ -48,6 +49,7 @@ import android.provider.Settings;
import android.util.EventLog;
import android.util.Slog;
import android.util.StatsLog;
+import android.view.WindowManagerPolicyConstants.OnReason;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.app.IBatteryStats;
@@ -136,6 +138,7 @@ public class Notifier {
// broadcasted state over the course of reporting the transition asynchronously.
private boolean mInteractive = true;
private int mInteractiveChangeReason;
+ private long mInteractiveChangeStartTime; // In SystemClock.uptimeMillis()
private boolean mInteractiveChanging;
// The pending interactive state that we will eventually want to broadcast.
@@ -371,7 +374,7 @@ public class Notifier {
* which case it will assume that the state did not fully converge before the
* next transition began and will recover accordingly.
*/
- public void onWakefulnessChangeStarted(final int wakefulness, int reason) {
+ public void onWakefulnessChangeStarted(final int wakefulness, int reason, long eventTime) {
final boolean interactive = PowerManagerInternal.isInteractive(wakefulness);
if (DEBUG) {
Slog.d(TAG, "onWakefulnessChangeStarted: wakefulness=" + wakefulness
@@ -410,6 +413,7 @@ public class Notifier {
// Handle early behaviors.
mInteractive = interactive;
mInteractiveChangeReason = reason;
+ mInteractiveChangeStartTime = eventTime;
mInteractiveChanging = true;
handleEarlyInteractiveChange();
}
@@ -440,8 +444,8 @@ public class Notifier {
mHandler.post(new Runnable() {
@Override
public void run() {
- // Note a SCREEN tron event is logged in PowerManagerService.
- mPolicy.startedWakingUp();
+ final int why = translateOnReason(mInteractiveChangeReason);
+ mPolicy.startedWakingUp(why);
}
});
@@ -470,12 +474,21 @@ public class Notifier {
*/
private void handleLateInteractiveChange() {
synchronized (mLock) {
+ final int interactiveChangeLatency =
+ (int) (SystemClock.uptimeMillis() - mInteractiveChangeStartTime);
if (mInteractive) {
// Finished waking up...
+ final int why = translateOnReason(mInteractiveChangeReason);
mHandler.post(new Runnable() {
@Override
public void run() {
- mPolicy.finishedWakingUp();
+ LogMaker log = new LogMaker(MetricsEvent.SCREEN);
+ log.setType(MetricsEvent.TYPE_OPEN);
+ log.setSubtype(why);
+ log.setLatency(interactiveChangeLatency);
+ MetricsLogger.action(log);
+ EventLogTags.writePowerScreenState(1, 0, 0, 0, interactiveChangeLatency);
+ mPolicy.finishedWakingUp(why);
}
});
} else {
@@ -499,8 +512,9 @@ public class Notifier {
LogMaker log = new LogMaker(MetricsEvent.SCREEN);
log.setType(MetricsEvent.TYPE_CLOSE);
log.setSubtype(why);
+ log.setLatency(interactiveChangeLatency);
MetricsLogger.action(log);
- EventLogTags.writePowerScreenState(0, why, 0, 0, 0);
+ EventLogTags.writePowerScreenState(0, why, 0, 0, interactiveChangeLatency);
mPolicy.finishedGoingToSleep(why);
}
});
@@ -524,6 +538,23 @@ public class Notifier {
}
}
+ private static @OnReason int translateOnReason(@WakeReason int reason) {
+ switch (reason) {
+ case PowerManager.WAKE_REASON_POWER_BUTTON:
+ case PowerManager.WAKE_REASON_PLUGGED_IN:
+ case PowerManager.WAKE_REASON_GESTURE:
+ case PowerManager.WAKE_REASON_CAMERA_LAUNCH:
+ case PowerManager.WAKE_REASON_WAKE_KEY:
+ case PowerManager.WAKE_REASON_WAKE_MOTION:
+ case PowerManager.WAKE_REASON_LID:
+ return WindowManagerPolicy.ON_BECAUSE_OF_USER;
+ case PowerManager.WAKE_REASON_APPLICATION:
+ return WindowManagerPolicy.ON_BECAUSE_OF_APPLICATION;
+ default:
+ return WindowManagerPolicy.ON_BECAUSE_OF_UNKNOWN;
+ }
+ }
+
/**
* Called when screen brightness boost begins or ends.
*/
@@ -565,14 +596,16 @@ public class Notifier {
/**
* Called when the screen has turned on.
*/
- public void onWakeUp(String reason, int reasonUid, String opPackageName, int opUid) {
+ public void onWakeUp(int reason, String details, int reasonUid, String opPackageName,
+ int opUid) {
if (DEBUG) {
- Slog.d(TAG, "onWakeUp: event=" + reason + ", reasonUid=" + reasonUid
+ Slog.d(TAG, "onWakeUp: reason=" + PowerManager.wakeReasonToString(reason)
+ + ", details=" + details + ", reasonUid=" + reasonUid
+ " opPackageName=" + opPackageName + " opUid=" + opUid);
}
try {
- mBatteryStats.noteWakeUp(reason, reasonUid);
+ mBatteryStats.noteWakeUp(details, reasonUid);
if (opPackageName != null) {
mAppOps.noteOpNoThrow(AppOpsManager.OP_TURN_SCREEN_ON, opUid, opPackageName);
}
diff --git a/services/core/java/com/android/server/power/PowerManagerService.java b/services/core/java/com/android/server/power/PowerManagerService.java
index 3ccd2341fbeb..af3bff0c96ba 100644
--- a/services/core/java/com/android/server/power/PowerManagerService.java
+++ b/services/core/java/com/android/server/power/PowerManagerService.java
@@ -39,7 +39,6 @@ import android.hardware.SystemSensorManager;
import android.hardware.display.DisplayManagerInternal;
import android.hardware.display.DisplayManagerInternal.DisplayPowerRequest;
import android.hardware.power.V1_0.PowerHint;
-import android.metrics.LogMaker;
import android.net.Uri;
import android.os.BatteryManager;
import android.os.BatteryManagerInternal;
@@ -52,6 +51,7 @@ import android.os.Looper;
import android.os.Message;
import android.os.PowerManager;
import android.os.PowerManager.ServiceType;
+import android.os.PowerManager.WakeReason;
import android.os.PowerManagerInternal;
import android.os.PowerSaveState;
import android.os.Process;
@@ -82,8 +82,6 @@ import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.app.IAppOpsService;
import com.android.internal.app.IBatteryStats;
import com.android.internal.hardware.AmbientDisplayConfiguration;
-import com.android.internal.logging.MetricsLogger;
-import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.internal.os.BackgroundThread;
import com.android.internal.util.DumpUtils;
import com.android.server.EventLogTags;
@@ -295,6 +293,7 @@ public final class PowerManagerService extends SystemService
private long mLastSleepTime;
// Last reason the device went to sleep.
+ private @WakeReason int mLastWakeReason;
private int mLastSleepReason;
// Timestamp of the last call to user activity.
@@ -1119,8 +1118,9 @@ public final class PowerManagerService extends SystemService
opPackageName = wakeLock.mPackageName;
opUid = wakeLock.mOwnerUid;
}
- wakeUpNoUpdateLocked(SystemClock.uptimeMillis(), wakeLock.mTag, opUid,
- opPackageName, opUid);
+ wakeUpNoUpdateLocked(SystemClock.uptimeMillis(),
+ PowerManager.WAKE_REASON_APPLICATION, wakeLock.mTag,
+ opUid, opPackageName, opUid);
}
}
@@ -1410,17 +1410,17 @@ public final class PowerManagerService extends SystemService
}
}
- private void wakeUpInternal(long eventTime, String reason, int uid, String opPackageName,
- int opUid) {
+ private void wakeUpInternal(long eventTime, @WakeReason int reason, String details, int uid,
+ String opPackageName, int opUid) {
synchronized (mLock) {
- if (wakeUpNoUpdateLocked(eventTime, reason, uid, opPackageName, opUid)) {
+ if (wakeUpNoUpdateLocked(eventTime, reason, details, uid, opPackageName, opUid)) {
updatePowerStateLocked();
}
}
}
- private boolean wakeUpNoUpdateLocked(long eventTime, String reason, int reasonUid,
- String opPackageName, int opUid) {
+ private boolean wakeUpNoUpdateLocked(long eventTime, @WakeReason int reason, String details,
+ int reasonUid, String opPackageName, int opUid) {
if (DEBUG_SPEW) {
Slog.d(TAG, "wakeUpNoUpdateLocked: eventTime=" + eventTime + ", uid=" + reasonUid);
}
@@ -1434,25 +1434,18 @@ public final class PowerManagerService extends SystemService
Trace.traceBegin(Trace.TRACE_TAG_POWER, "wakeUp");
try {
- switch (mWakefulness) {
- case WAKEFULNESS_ASLEEP:
- Slog.i(TAG, "Waking up from sleep (uid=" + reasonUid + " reason=" + reason
- + ")...");
- break;
- case WAKEFULNESS_DREAMING:
- Slog.i(TAG, "Waking up from dream (uid=" + reasonUid + " reason=" + reason
- + ")...");
- break;
- case WAKEFULNESS_DOZING:
- Slog.i(TAG, "Waking up from dozing (uid=" + reasonUid + " reason=" + reason
- + ")...");
- break;
- }
+ Slog.i(TAG, "Waking up from "
+ + PowerManagerInternal.wakefulnessToString(mWakefulness)
+ + " (uid=" + reasonUid
+ + ", reason=" + PowerManager.wakeReasonToString(reason)
+ + ", details=" + details
+ + ")...");
mLastWakeTime = eventTime;
- setWakefulnessLocked(WAKEFULNESS_AWAKE, 0);
+ mLastWakeReason = reason;
+ setWakefulnessLocked(WAKEFULNESS_AWAKE, reason, eventTime);
- mNotifier.onWakeUp(reason, reasonUid, opPackageName, opUid);
+ mNotifier.onWakeUp(reason, details, reasonUid, opPackageName, opUid);
userActivityNoUpdateLocked(
eventTime, PowerManager.USER_ACTIVITY_EVENT_OTHER, 0, reasonUid);
} finally {
@@ -1520,7 +1513,7 @@ public final class PowerManagerService extends SystemService
mLastSleepTime = eventTime;
mLastSleepReason = reason;
mSandmanSummoned = true;
- setWakefulnessLocked(WAKEFULNESS_DOZING, reason);
+ setWakefulnessLocked(WAKEFULNESS_DOZING, reason, eventTime);
// Report the number of wake locks that will be cleared by going to sleep.
int numWakeLocksCleared = 0;
@@ -1570,7 +1563,7 @@ public final class PowerManagerService extends SystemService
Slog.i(TAG, "Nap time (uid " + uid +")...");
mSandmanSummoned = true;
- setWakefulnessLocked(WAKEFULNESS_DREAMING, 0);
+ setWakefulnessLocked(WAKEFULNESS_DREAMING, 0, eventTime);
} finally {
Trace.traceEnd(Trace.TRACE_TAG_POWER);
}
@@ -1593,7 +1586,8 @@ public final class PowerManagerService extends SystemService
try {
Slog.i(TAG, "Sleeping (uid " + uid +")...");
- setWakefulnessLocked(WAKEFULNESS_ASLEEP, PowerManager.GO_TO_SLEEP_REASON_TIMEOUT);
+ setWakefulnessLocked(WAKEFULNESS_ASLEEP, PowerManager.GO_TO_SLEEP_REASON_TIMEOUT,
+ eventTime);
} finally {
Trace.traceEnd(Trace.TRACE_TAG_POWER);
}
@@ -1601,13 +1595,13 @@ public final class PowerManagerService extends SystemService
}
@VisibleForTesting
- void setWakefulnessLocked(int wakefulness, int reason) {
+ void setWakefulnessLocked(int wakefulness, int reason, long eventTime) {
if (mWakefulness != wakefulness) {
mWakefulness = wakefulness;
mWakefulnessChanging = true;
mDirty |= DIRTY_WAKEFULNESS;
if (mNotifier != null) {
- mNotifier.onWakefulnessChangeStarted(wakefulness, reason);
+ mNotifier.onWakefulnessChangeStarted(wakefulness, reason, eventTime);
}
mAttentionDetector.onWakefulnessChangeStarted(wakefulness);
}
@@ -1631,23 +1625,6 @@ public final class PowerManagerService extends SystemService
}
}
- private void logScreenOn() {
- Trace.asyncTraceEnd(Trace.TRACE_TAG_POWER, TRACE_SCREEN_ON, 0);
-
- final int latencyMs = (int) (SystemClock.uptimeMillis() - mLastWakeTime);
-
- LogMaker log = new LogMaker(MetricsEvent.SCREEN);
- log.setType(MetricsEvent.TYPE_OPEN);
- log.setSubtype(0); // not user initiated
- log.setLatency(latencyMs); // How long it took.
- MetricsLogger.action(log);
- EventLogTags.writePowerScreenState(1, 0, 0, 0, latencyMs);
-
- if (latencyMs >= SCREEN_ON_LATENCY_WARNING_MS) {
- Slog.w(TAG, "Screen on took " + latencyMs+ " ms");
- }
- }
-
private void finishWakefulnessChangeIfNeededLocked() {
if (mWakefulnessChanging && mDisplayReady) {
if (mWakefulness == WAKEFULNESS_DOZING
@@ -1658,7 +1635,11 @@ public final class PowerManagerService extends SystemService
logSleepTimeoutRecapturedLocked();
}
if (mWakefulness == WAKEFULNESS_AWAKE) {
- logScreenOn();
+ Trace.asyncTraceEnd(Trace.TRACE_TAG_POWER, TRACE_SCREEN_ON, 0);
+ final int latencyMs = (int) (SystemClock.uptimeMillis() - mLastWakeTime);
+ if (latencyMs >= SCREEN_ON_LATENCY_WARNING_MS) {
+ Slog.w(TAG, "Screen on took " + latencyMs + " ms");
+ }
}
mWakefulnessChanging = false;
mNotifier.onWakefulnessChangeFinished();
@@ -1786,7 +1767,8 @@ public final class PowerManagerService extends SystemService
final long now = SystemClock.uptimeMillis();
if (shouldWakeUpWhenPluggedOrUnpluggedLocked(wasPowered, oldPlugType,
dockedOnWirelessCharger)) {
- wakeUpNoUpdateLocked(now, "android.server.power:POWER", Process.SYSTEM_UID,
+ wakeUpNoUpdateLocked(now, PowerManager.WAKE_REASON_PLUGGED_IN,
+ "android.server.power:PLUGGED:" + mIsPowered, Process.SYSTEM_UID,
mContext.getOpPackageName(), Process.SYSTEM_UID);
}
userActivityNoUpdateLocked(
@@ -2369,8 +2351,10 @@ public final class PowerManagerService extends SystemService
PowerManager.GO_TO_SLEEP_REASON_TIMEOUT, 0, Process.SYSTEM_UID);
updatePowerStateLocked();
} else {
- wakeUpNoUpdateLocked(SystemClock.uptimeMillis(), "android.server.power:DREAM",
- Process.SYSTEM_UID, mContext.getOpPackageName(), Process.SYSTEM_UID);
+ wakeUpNoUpdateLocked(SystemClock.uptimeMillis(),
+ PowerManager.WAKE_REASON_UNKNOWN,
+ "android.server.power:DREAM_FINISHED", Process.SYSTEM_UID,
+ mContext.getOpPackageName(), Process.SYSTEM_UID);
updatePowerStateLocked();
}
} else if (wakefulness == WAKEFULNESS_DOZING) {
@@ -4375,7 +4359,8 @@ public final class PowerManagerService extends SystemService
}
@Override // Binder call
- public void wakeUp(long eventTime, String reason, String opPackageName) {
+ public void wakeUp(long eventTime, @WakeReason int reason, String details,
+ String opPackageName) {
if (eventTime > SystemClock.uptimeMillis()) {
throw new IllegalArgumentException("event time must not be in the future");
}
@@ -4386,7 +4371,7 @@ public final class PowerManagerService extends SystemService
final int uid = Binder.getCallingUid();
final long ident = Binder.clearCallingIdentity();
try {
- wakeUpInternal(eventTime, reason, uid, opPackageName, uid);
+ wakeUpInternal(eventTime, reason, details, uid, opPackageName, uid);
} finally {
Binder.restoreCallingIdentity(ident);
}
diff --git a/services/core/java/com/android/server/power/batterysaver/BatterySaverPolicy.java b/services/core/java/com/android/server/power/batterysaver/BatterySaverPolicy.java
index bd46a50f97de..fac95f9af42c 100644
--- a/services/core/java/com/android/server/power/batterysaver/BatterySaverPolicy.java
+++ b/services/core/java/com/android/server/power/batterysaver/BatterySaverPolicy.java
@@ -665,8 +665,7 @@ public class BatterySaverPolicy extends ContentObserver {
config.getEnableAdjustBrightness(),
config.getEnableDataSaver(),
config.getEnableFirewall(),
- // TODO: add option to config
- config.getAdvertiseIsEnabled(),
+ config.getEnableNightMode(),
config.getEnableQuickDoze(),
/* filesForInteractive */
(new CpuFrequencies()).parseString(cpuFreqInteractive).toSysFileMap(),
@@ -674,7 +673,7 @@ public class BatterySaverPolicy extends ContentObserver {
(new CpuFrequencies()).parseString(cpuFreqNoninteractive).toSysFileMap(),
config.getForceAllAppsStandby(),
config.getForceBackgroundCheck(),
- config.getGpsMode()
+ config.getLocationMode()
);
}
diff --git a/services/core/java/com/android/server/rollback/RollbackManagerServiceImpl.java b/services/core/java/com/android/server/rollback/RollbackManagerServiceImpl.java
index 24d5bd14bc44..95c3f4c43313 100644
--- a/services/core/java/com/android/server/rollback/RollbackManagerServiceImpl.java
+++ b/services/core/java/com/android/server/rollback/RollbackManagerServiceImpl.java
@@ -340,12 +340,9 @@ class RollbackManagerServiceImpl extends IRollbackManager.Stub {
// for apex?
if (!info.isApex()) {
String installerPackageName = pm.getInstallerPackageName(info.getPackageName());
- if (installerPackageName == null) {
- sendFailure(statusReceiver, RollbackManager.STATUS_FAILURE,
- "Cannot find installer package");
- return;
+ if (installerPackageName != null) {
+ params.setInstallerPackageName(installerPackageName);
}
- params.setInstallerPackageName(installerPackageName);
}
params.setAllowDowngrade(true);
if (data.isStaged()) {
diff --git a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
index 071dde74f103..b0ef8a0d4209 100644
--- a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
+++ b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
@@ -2243,9 +2243,12 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
synchronized (mLock) {
mInAmbientMode = inAmbientMode;
final WallpaperData data = mWallpaperMap.get(mCurrentUserId);
+ final boolean hasConnection = data != null && data.connection != null;
+ final WallpaperInfo info = hasConnection ? data.connection.mInfo : null;
+
// The wallpaper info is null for image wallpaper, also use the engine in this case.
- if (data != null && data.connection != null && (data.connection.mInfo == null
- || data.connection.mInfo.supportsAmbientMode())) {
+ if (hasConnection && (info == null && isAodImageWallpaperEnabled()
+ || info != null && info.supportsAmbientMode())) {
// TODO(multi-display) Extends this method with specific display.
engine = data.connection.getDisplayConnectorOrCreate(DEFAULT_DISPLAY).mEngine;
} else {
diff --git a/services/core/java/com/android/server/wm/ActivityStackSupervisor.java b/services/core/java/com/android/server/wm/ActivityStackSupervisor.java
index c0fe6e937422..0a3c2fba3930 100644
--- a/services/core/java/com/android/server/wm/ActivityStackSupervisor.java
+++ b/services/core/java/com/android/server/wm/ActivityStackSupervisor.java
@@ -97,7 +97,6 @@ import android.app.servertransaction.LaunchActivityItem;
import android.app.servertransaction.PauseActivityItem;
import android.app.servertransaction.ResumeActivityItem;
import android.content.ComponentName;
-import android.content.Context;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.content.pm.ApplicationInfo;
@@ -467,7 +466,7 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks {
* initialized. So we initialize our wakelocks afterwards.
*/
void initPowerManagement() {
- mPowerManager = (PowerManager)mService.mContext.getSystemService(Context.POWER_SERVICE);
+ mPowerManager = mService.mContext.getSystemService(PowerManager.class);
mGoingToSleep = mPowerManager
.newWakeLock(PARTIAL_WAKE_LOCK, "ActivityManager-Sleep");
mLaunchingActivity = mPowerManager.newWakeLock(PARTIAL_WAKE_LOCK, "*launch*");
@@ -2456,7 +2455,8 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks {
}
void wakeUp(String reason) {
- mPowerManager.wakeUp(SystemClock.uptimeMillis(), "android.server.am:TURN_ON:" + reason);
+ mPowerManager.wakeUp(SystemClock.uptimeMillis(), PowerManager.WAKE_REASON_APPLICATION,
+ "android.server.am:TURN_ON:" + reason);
}
/**
diff --git a/services/core/java/com/android/server/wm/AppWindowThumbnail.java b/services/core/java/com/android/server/wm/AppWindowThumbnail.java
index 6fcc331bf62f..0e14e46e77de 100644
--- a/services/core/java/com/android/server/wm/AppWindowThumbnail.java
+++ b/services/core/java/com/android/server/wm/AppWindowThumbnail.java
@@ -143,7 +143,7 @@ class AppWindowThumbnail implements Animatable {
void destroy() {
mSurfaceAnimator.cancelAnimation();
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
}
/**
diff --git a/services/core/java/com/android/server/wm/AppWindowToken.java b/services/core/java/com/android/server/wm/AppWindowToken.java
index 3246a8702cd1..2cc85e2076e0 100644
--- a/services/core/java/com/android/server/wm/AppWindowToken.java
+++ b/services/core/java/com/android/server/wm/AppWindowToken.java
@@ -2504,7 +2504,7 @@ class AppWindowToken extends WindowToken implements WindowManagerService.AppFree
public void onAnimationLeashDestroyed(Transaction t) {
super.onAnimationLeashDestroyed(t);
if (mAnimationBoundsLayer != null) {
- t.reparent(mAnimationBoundsLayer, null);
+ t.remove(mAnimationBoundsLayer);
mAnimationBoundsLayer = null;
}
diff --git a/services/core/java/com/android/server/wm/BlackFrame.java b/services/core/java/com/android/server/wm/BlackFrame.java
index c90f5bfb7ee0..497e4121f12e 100644
--- a/services/core/java/com/android/server/wm/BlackFrame.java
+++ b/services/core/java/com/android/server/wm/BlackFrame.java
@@ -153,7 +153,7 @@ public class BlackFrame {
if (mBlackSurfaces[i] != null) {
if (SHOW_TRANSACTIONS || SHOW_SURFACE_ALLOC) Slog.i(TAG_WM,
" BLACK " + mBlackSurfaces[i].surface + ": DESTROY");
- mBlackSurfaces[i].surface.destroy();
+ mBlackSurfaces[i].surface.remove();
mBlackSurfaces[i] = null;
}
}
diff --git a/services/core/java/com/android/server/wm/Dimmer.java b/services/core/java/com/android/server/wm/Dimmer.java
index c39060ee1922..1373e1879d14 100644
--- a/services/core/java/com/android/server/wm/Dimmer.java
+++ b/services/core/java/com/android/server/wm/Dimmer.java
@@ -129,7 +129,7 @@ class Dimmer {
final DimAnimatable dimAnimatable = new DimAnimatable(dimLayer);
mSurfaceAnimator = new SurfaceAnimator(dimAnimatable, () -> {
if (!mDimming) {
- dimAnimatable.getPendingTransaction().reparent(mDimLayer, null);
+ dimAnimatable.getPendingTransaction().remove(mDimLayer);
}
}, mHost.mWmService);
}
@@ -300,7 +300,7 @@ class Dimmer {
if (!mDimState.mDimming) {
if (!mDimState.mAnimateExit) {
- t.reparent(mDimState.mDimLayer, null);
+ t.remove(mDimState.mDimLayer);
} else {
startDimExit(mLastRequestedDimContainer, mDimState.mSurfaceAnimator, t);
}
diff --git a/services/core/java/com/android/server/wm/DisplayContent.java b/services/core/java/com/android/server/wm/DisplayContent.java
index 7a8fd49361b6..928b57cf050b 100644
--- a/services/core/java/com/android/server/wm/DisplayContent.java
+++ b/services/core/java/com/android/server/wm/DisplayContent.java
@@ -4418,13 +4418,13 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
.show(mSplitScreenDividerAnchor);
scheduleAnimation();
} else {
- mAppAnimationLayer.destroy();
+ mAppAnimationLayer.remove();
mAppAnimationLayer = null;
- mBoostedAppAnimationLayer.destroy();
+ mBoostedAppAnimationLayer.remove();
mBoostedAppAnimationLayer = null;
- mHomeAppAnimationLayer.destroy();
+ mHomeAppAnimationLayer.remove();
mHomeAppAnimationLayer = null;
- mSplitScreenDividerAnchor.destroy();
+ mSplitScreenDividerAnchor.remove();
mSplitScreenDividerAnchor = null;
}
}
diff --git a/services/core/java/com/android/server/wm/Letterbox.java b/services/core/java/com/android/server/wm/Letterbox.java
index 434084cc1f3d..987492024546 100644
--- a/services/core/java/com/android/server/wm/Letterbox.java
+++ b/services/core/java/com/android/server/wm/Letterbox.java
@@ -107,10 +107,10 @@ public class Letterbox {
mOuter.setEmpty();
mInner.setEmpty();
- mTop.destroy();
- mLeft.destroy();
- mBottom.destroy();
- mRight.destroy();
+ mTop.remove();
+ mLeft.remove();
+ mBottom.remove();
+ mRight.remove();
}
/** Returns whether a call to {@link #applySurfaceChanges} would change the surface. */
@@ -154,9 +154,9 @@ public class Letterbox {
mSurface.setColor(new float[]{0, 0, 0});
}
- public void destroy() {
+ public void remove() {
if (mSurface != null) {
- mSurface.destroy();
+ mSurface.remove();
mSurface = null;
}
}
diff --git a/services/core/java/com/android/server/wm/ScreenRotationAnimation.java b/services/core/java/com/android/server/wm/ScreenRotationAnimation.java
index 3947bd47b588..84cd8d1632cf 100644
--- a/services/core/java/com/android/server/wm/ScreenRotationAnimation.java
+++ b/services/core/java/com/android/server/wm/ScreenRotationAnimation.java
@@ -626,7 +626,7 @@ class ScreenRotationAnimation {
if (SHOW_TRANSACTIONS ||
SHOW_SURFACE_ALLOC) Slog.i(TAG_WM,
" FREEZE " + mSurfaceControl + ": DESTROY");
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
mSurfaceControl = null;
}
if (mCustomBlackFrame != null) {
diff --git a/services/core/java/com/android/server/wm/SurfaceAnimator.java b/services/core/java/com/android/server/wm/SurfaceAnimator.java
index c600e0f4a657..5ea24518370b 100644
--- a/services/core/java/com/android/server/wm/SurfaceAnimator.java
+++ b/services/core/java/com/android/server/wm/SurfaceAnimator.java
@@ -280,7 +280,7 @@ class SurfaceAnimator {
}
mService.mAnimationTransferMap.remove(mAnimation);
if (mLeash != null && destroyLeash) {
- t.reparent(mLeash, null);
+ t.remove(mLeash);
scheduleAnim = true;
}
mLeash = null;
diff --git a/services/core/java/com/android/server/wm/TaskStack.java b/services/core/java/com/android/server/wm/TaskStack.java
index 53cd5ea8bf16..7b742fd2e0f3 100644
--- a/services/core/java/com/android/server/wm/TaskStack.java
+++ b/services/core/java/com/android/server/wm/TaskStack.java
@@ -1006,7 +1006,7 @@ public class TaskStack extends WindowContainer<Task> implements
EventLog.writeEvent(EventLogTags.WM_STACK_REMOVED, mStackId);
if (mAnimationBackgroundSurface != null) {
- mAnimationBackgroundSurface.destroy();
+ mAnimationBackgroundSurface.remove();
mAnimationBackgroundSurface = null;
}
diff --git a/services/core/java/com/android/server/wm/WindowContainer.java b/services/core/java/com/android/server/wm/WindowContainer.java
index a054148e26b9..76f080b233a8 100644
--- a/services/core/java/com/android/server/wm/WindowContainer.java
+++ b/services/core/java/com/android/server/wm/WindowContainer.java
@@ -320,7 +320,7 @@ class WindowContainer<E extends WindowContainer> extends ConfigurationContainer<
}
if (mSurfaceControl != null) {
- mPendingTransaction.reparent(mSurfaceControl, null);
+ mPendingTransaction.remove(mSurfaceControl);
// Merge to parent transaction to ensure the transactions on this WindowContainer are
// applied in native even if WindowContainer is removed.
diff --git a/services/core/java/com/android/server/wm/WindowState.java b/services/core/java/com/android/server/wm/WindowState.java
index 4bc140095f1b..85b251a99f83 100644
--- a/services/core/java/com/android/server/wm/WindowState.java
+++ b/services/core/java/com/android/server/wm/WindowState.java
@@ -156,6 +156,7 @@ import android.os.Binder;
import android.os.Debug;
import android.os.IBinder;
import android.os.PowerManager;
+import android.os.PowerManager.WakeReason;
import android.os.RemoteCallbackList;
import android.os.RemoteException;
import android.os.SystemClock;
@@ -611,7 +612,7 @@ class WindowState extends WindowContainer<WindowState> implements WindowManagerP
}
interface PowerManagerWrapper {
- void wakeUp(long time, String reason);
+ void wakeUp(long time, @WakeReason int reason, String details);
boolean isInteractive();
@@ -623,8 +624,8 @@ class WindowState extends WindowContainer<WindowState> implements WindowManagerP
this(service, s, c, token, parentWindow, appOp, seq, a, viewVisibility, ownerId,
ownerCanAddInternalSystemWindow, new PowerManagerWrapper() {
@Override
- public void wakeUp(long time, String reason) {
- service.mPowerManager.wakeUp(time, reason);
+ public void wakeUp(long time, @WakeReason int reason, String details) {
+ service.mPowerManager.wakeUp(time, reason, details);
}
@Override
@@ -2253,7 +2254,7 @@ class WindowState extends WindowContainer<WindowState> implements WindowManagerP
Slog.v(TAG, "Relayout window turning screen on: " + this);
}
mPowerManagerWrapper.wakeUp(SystemClock.uptimeMillis(),
- "android.server.wm:TURN_ON");
+ PowerManager.WAKE_REASON_APPLICATION, "android.server.wm:SCREEN_ON_FLAG");
}
if (mAppToken != null) {
diff --git a/services/core/java/com/android/server/wm/WindowSurfaceController.java b/services/core/java/com/android/server/wm/WindowSurfaceController.java
index dea3597989be..e796b99f3989 100644
--- a/services/core/java/com/android/server/wm/WindowSurfaceController.java
+++ b/services/core/java/com/android/server/wm/WindowSurfaceController.java
@@ -161,7 +161,7 @@ class WindowSurfaceController {
}
try {
if (mSurfaceControl != null) {
- mSurfaceControl.destroy();
+ mSurfaceControl.remove();
}
} catch (RuntimeException e) {
Slog.w(TAG, "Error destroying surface in: " + this, e);
diff --git a/services/robotests/src/com/android/server/backup/encryption/chunking/ByteRangeTest.java b/services/robotests/src/com/android/server/backup/encryption/chunking/ByteRangeTest.java
new file mode 100644
index 000000000000..8df08262c9fa
--- /dev/null
+++ b/services/robotests/src/com/android/server/backup/encryption/chunking/ByteRangeTest.java
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import static org.junit.Assert.assertEquals;
+import static org.testng.Assert.assertThrows;
+
+import android.platform.test.annotations.Presubmit;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.robolectric.RobolectricTestRunner;
+
+/** Tests for {@link ByteRange}. */
+@RunWith(RobolectricTestRunner.class)
+@Presubmit
+public class ByteRangeTest {
+ @Test
+ public void getLength_includesEnd() throws Exception {
+ ByteRange byteRange = new ByteRange(5, 10);
+
+ int length = byteRange.getLength();
+
+ assertEquals(6, length);
+ }
+
+ @Test
+ public void constructor_rejectsNegativeStart() {
+ assertThrows(IllegalArgumentException.class, () -> new ByteRange(-1, 10));
+ }
+
+ @Test
+ public void constructor_rejectsEndBeforeStart() {
+ assertThrows(IllegalArgumentException.class, () -> new ByteRange(10, 9));
+ }
+
+ @Test
+ public void extend_withZeroLength_throwsException() {
+ ByteRange byteRange = new ByteRange(5, 10);
+
+ assertThrows(IllegalArgumentException.class, () -> byteRange.extend(0));
+ }
+}
diff --git a/services/robotests/src/com/android/server/backup/encryption/chunking/DiffScriptBackupWriterTest.java b/services/robotests/src/com/android/server/backup/encryption/chunking/DiffScriptBackupWriterTest.java
new file mode 100644
index 000000000000..2af6f2bee8ff
--- /dev/null
+++ b/services/robotests/src/com/android/server/backup/encryption/chunking/DiffScriptBackupWriterTest.java
@@ -0,0 +1,90 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.mockito.Mockito.atLeastOnce;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+
+import android.platform.test.annotations.Presubmit;
+
+import com.google.common.primitives.Bytes;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.ArgumentCaptor;
+import org.mockito.Captor;
+import org.mockito.Mock;
+import org.robolectric.RobolectricTestRunner;
+
+import java.io.IOException;
+
+/** Tests for {@link DiffScriptBackupWriter}. */
+@RunWith(RobolectricTestRunner.class)
+@Presubmit
+public class DiffScriptBackupWriterTest {
+ private static final byte[] TEST_BYTES = {1, 2, 3, 4, 5, 6, 7, 8, 9};
+
+ @Captor private ArgumentCaptor<Byte> mBytesCaptor;
+ @Mock private SingleStreamDiffScriptWriter mDiffScriptWriter;
+ private BackupWriter mBackupWriter;
+
+ @Before
+ public void setUp() {
+ mDiffScriptWriter = mock(SingleStreamDiffScriptWriter.class);
+ mBackupWriter = new DiffScriptBackupWriter(mDiffScriptWriter);
+ mBytesCaptor = ArgumentCaptor.forClass(Byte.class);
+ }
+
+ @Test
+ public void writeBytes_writesBytesToWriter() throws Exception {
+ mBackupWriter.writeBytes(TEST_BYTES);
+
+ verify(mDiffScriptWriter, atLeastOnce()).writeByte(mBytesCaptor.capture());
+ assertThat(mBytesCaptor.getAllValues())
+ .containsExactlyElementsIn(Bytes.asList(TEST_BYTES))
+ .inOrder();
+ }
+
+ @Test
+ public void writeChunk_writesChunkToWriter() throws Exception {
+ mBackupWriter.writeChunk(0, 10);
+
+ verify(mDiffScriptWriter).writeChunk(0, 10);
+ }
+
+ @Test
+ public void getBytesWritten_returnsTotalSum() throws Exception {
+ mBackupWriter.writeBytes(TEST_BYTES);
+ mBackupWriter.writeBytes(TEST_BYTES);
+ mBackupWriter.writeChunk(/*start=*/ 0, /*length=*/ 10);
+
+ long bytesWritten = mBackupWriter.getBytesWritten();
+
+ assertThat(bytesWritten).isEqualTo(2 * TEST_BYTES.length + 10);
+ }
+
+ @Test
+ public void flush_flushesWriter() throws IOException {
+ mBackupWriter.flush();
+
+ verify(mDiffScriptWriter).flush();
+ }
+}
diff --git a/services/robotests/src/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriterTest.java b/services/robotests/src/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriterTest.java
new file mode 100644
index 000000000000..73baf80a2c70
--- /dev/null
+++ b/services/robotests/src/com/android/server/backup/encryption/chunking/SingleStreamDiffScriptWriterTest.java
@@ -0,0 +1,128 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.backup.encryption.chunking;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+import static org.testng.Assert.assertThrows;
+
+import android.platform.test.annotations.Presubmit;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.robolectric.RobolectricTestRunner;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.util.Locale;
+
+/** Tests for {@link SingleStreamDiffScriptWriter}. */
+@RunWith(RobolectricTestRunner.class)
+@Presubmit
+public class SingleStreamDiffScriptWriterTest {
+ private static final int MAX_CHUNK_SIZE_IN_BYTES = 256;
+ /** By default this Locale does not use Arabic numbers for %d formatting. */
+ private static final Locale HINDI = new Locale("hi", "IN");
+
+ private Locale mDefaultLocale;
+ private ByteArrayOutputStream mOutputStream;
+ private SingleStreamDiffScriptWriter mDiffScriptWriter;
+
+ @Before
+ public void setUp() {
+ mDefaultLocale = Locale.getDefault();
+ mOutputStream = new ByteArrayOutputStream();
+ mDiffScriptWriter =
+ new SingleStreamDiffScriptWriter(mOutputStream, MAX_CHUNK_SIZE_IN_BYTES);
+ }
+
+ @After
+ public void tearDown() {
+ Locale.setDefault(mDefaultLocale);
+ }
+
+ @Test
+ public void writeChunk_withNegativeStart_throwsException() {
+ assertThrows(
+ IllegalArgumentException.class,
+ () -> mDiffScriptWriter.writeChunk(-1, 50));
+ }
+
+ @Test
+ public void writeChunk_withZeroLength_throwsException() {
+ assertThrows(
+ IllegalArgumentException.class,
+ () -> mDiffScriptWriter.writeChunk(0, 0));
+ }
+
+ @Test
+ public void writeChunk_withExistingBytesInBuffer_writesBufferFirst()
+ throws IOException {
+ String testString = "abcd";
+ writeStringAsBytesToWriter(testString, mDiffScriptWriter);
+
+ mDiffScriptWriter.writeChunk(0, 20);
+ mDiffScriptWriter.flush();
+
+ // Expected format: length of abcd, newline, abcd, newline, chunk start - chunk end
+ assertThat(mOutputStream.toString("UTF-8")).isEqualTo(
+ String.format("%d\n%s\n%d-%d\n", testString.length(), testString, 0, 19));
+ }
+
+ @Test
+ public void writeChunk_overlappingPreviousChunk_combinesChunks() throws IOException {
+ mDiffScriptWriter.writeChunk(3, 4);
+
+ mDiffScriptWriter.writeChunk(7, 5);
+ mDiffScriptWriter.flush();
+
+ assertThat(mOutputStream.toString("UTF-8")).isEqualTo(String.format("3-11\n"));
+ }
+
+ @Test
+ public void writeChunk_formatsByteIndexesUsingArabicNumbers() throws Exception {
+ Locale.setDefault(HINDI);
+
+ mDiffScriptWriter.writeChunk(0, 12345);
+ mDiffScriptWriter.flush();
+
+ assertThat(mOutputStream.toString("UTF-8")).isEqualTo("0-12344\n");
+ }
+
+ @Test
+ public void flush_flushesOutputStream() throws IOException {
+ ByteArrayOutputStream mockOutputStream = mock(ByteArrayOutputStream.class);
+ SingleStreamDiffScriptWriter diffScriptWriter =
+ new SingleStreamDiffScriptWriter(mockOutputStream, MAX_CHUNK_SIZE_IN_BYTES);
+
+ diffScriptWriter.flush();
+
+ verify(mockOutputStream).flush();
+ }
+
+ private void writeStringAsBytesToWriter(String string, SingleStreamDiffScriptWriter writer)
+ throws IOException {
+ byte[] bytes = string.getBytes("UTF-8");
+ for (int i = 0; i < bytes.length; i++) {
+ writer.writeByte(bytes[i]);
+ }
+ }
+}
diff --git a/services/tests/servicestests/src/com/android/server/display/BrightnessTrackerTest.java b/services/tests/servicestests/src/com/android/server/display/BrightnessTrackerTest.java
index e3b1245f20a5..7081d2e3b370 100644
--- a/services/tests/servicestests/src/com/android/server/display/BrightnessTrackerTest.java
+++ b/services/tests/servicestests/src/com/android/server/display/BrightnessTrackerTest.java
@@ -962,13 +962,13 @@ public class BrightnessTrackerTest {
}
@Override
- public int getColorTemperature(Context context, int userId) {
+ public int getNightDisplayColorTemperature(Context context) {
return mSecureIntSettings.getOrDefault(Settings.Secure.NIGHT_DISPLAY_COLOR_TEMPERATURE,
mDefaultNightModeColorTemperature);
}
@Override
- public boolean isNightModeActive(Context context, int userId) {
+ public boolean isNightDisplayActivated(Context context) {
return mSecureIntSettings.getOrDefault(Settings.Secure.NIGHT_DISPLAY_ACTIVATED,
0) == 1;
}
diff --git a/services/tests/servicestests/src/com/android/server/display/ColorDisplayServiceTest.java b/services/tests/servicestests/src/com/android/server/display/ColorDisplayServiceTest.java
index 0b01657868a8..5900fc57296c 100644
--- a/services/tests/servicestests/src/com/android/server/display/ColorDisplayServiceTest.java
+++ b/services/tests/servicestests/src/com/android/server/display/ColorDisplayServiceTest.java
@@ -26,6 +26,7 @@ import android.app.AlarmManager;
import android.content.Context;
import android.content.ContextWrapper;
import android.hardware.display.ColorDisplayManager;
+import android.hardware.display.Time;
import android.os.Handler;
import android.os.UserHandle;
import android.provider.Settings;
@@ -37,7 +38,6 @@ import androidx.test.InstrumentationRegistry;
import androidx.test.runner.AndroidJUnit4;
import com.android.internal.R;
-import com.android.internal.app.ColorDisplayController;
import com.android.internal.util.test.FakeSettingsProvider;
import com.android.server.LocalServices;
import com.android.server.SystemService;
@@ -71,7 +71,6 @@ public class ColorDisplayServiceTest {
private MockTwilightManager mTwilightManager;
private ColorDisplayService mColorDisplayService;
- private ColorDisplayController mColorDisplayController;
private ColorDisplayService.BinderService mBinderService;
@BeforeClass
@@ -97,7 +96,6 @@ public class ColorDisplayServiceTest {
mTwilightManager = new MockTwilightManager();
LocalServices.addService(TwilightManager.class, mTwilightManager);
- mColorDisplayController = new ColorDisplayController(mContext, mUserId);
mColorDisplayService = new ColorDisplayService(mContext);
mBinderService = mColorDisplayService.new BinderService();
}
@@ -988,9 +986,11 @@ public class ColorDisplayServiceTest {
* @param endTimeOffset the offset relative to now to deactivate Night display (in minutes)
*/
private void setAutoModeCustom(int startTimeOffset, int endTimeOffset) {
- mColorDisplayController.setAutoMode(ColorDisplayManager.AUTO_MODE_CUSTOM_TIME);
- mColorDisplayController.setCustomStartTime(getLocalTimeRelativeToNow(startTimeOffset));
- mColorDisplayController.setCustomEndTime(getLocalTimeRelativeToNow(endTimeOffset));
+ mBinderService.setNightDisplayAutoMode(ColorDisplayManager.AUTO_MODE_CUSTOM_TIME);
+ mBinderService.setNightDisplayCustomStartTime(
+ new Time(getLocalTimeRelativeToNow(startTimeOffset)));
+ mBinderService
+ .setNightDisplayCustomEndTime(new Time(getLocalTimeRelativeToNow(endTimeOffset)));
}
/**
@@ -1000,7 +1000,7 @@ public class ColorDisplayServiceTest {
* @param sunriseOffset the offset relative to now for sunrise (in minutes)
*/
private void setAutoModeTwilight(int sunsetOffset, int sunriseOffset) {
- mColorDisplayController.setAutoMode(ColorDisplayManager.AUTO_MODE_TWILIGHT);
+ mBinderService.setNightDisplayAutoMode(ColorDisplayManager.AUTO_MODE_TWILIGHT);
mTwilightManager.setTwilightState(
getTwilightStateRelativeToNow(sunsetOffset, sunriseOffset));
}
@@ -1041,22 +1041,18 @@ public class ColorDisplayServiceTest {
}
/**
- * Configures color mode via ColorDisplayController.
- *
- * @param colorMode the color mode to set
+ * Configures color mode.
*/
private void setColorMode(int colorMode) {
- mColorDisplayController.setColorMode(colorMode);
+ mBinderService.setColorMode(colorMode);
}
/**
* Returns whether the color mode is valid on the device the tests are running on.
- *
- * @param mode the mode to check
*/
private boolean isColorModeValid(int mode) {
final int[] availableColorModes = mContext.getResources().getIntArray(
- R.array.config_availableColorModes);
+ R.array.config_availableColorModes);
if (availableColorModes != null) {
for (int availableMode : availableColorModes) {
if (mode == availableMode) {
@@ -1073,12 +1069,9 @@ public class ColorDisplayServiceTest {
private void startService() {
Secure.putIntForUser(mContext.getContentResolver(), Secure.USER_SETUP_COMPLETE, 1, mUserId);
- InstrumentationRegistry.getInstrumentation().runOnMainSync(new Runnable() {
- @Override
- public void run() {
- mColorDisplayService.onBootPhase(SystemService.PHASE_BOOT_COMPLETED);
- mColorDisplayService.onStartUser(mUserId);
- }
+ InstrumentationRegistry.getInstrumentation().runOnMainSync(() -> {
+ mColorDisplayService.onBootPhase(SystemService.PHASE_BOOT_COMPLETED);
+ mColorDisplayService.onStartUser(mUserId);
});
}
@@ -1100,7 +1093,7 @@ public class ColorDisplayServiceTest {
*/
private void assertActiveColorMode(int mode) {
assertWithMessage("Unexpected color mode setting")
- .that(mColorDisplayController.getColorMode())
+ .that(mBinderService.getColorMode())
.isEqualTo(mode);
}
diff --git a/services/tests/servicestests/src/com/android/server/pm/PackageParserTest.java b/services/tests/servicestests/src/com/android/server/pm/PackageParserTest.java
index 85909d564a7b..72357ceee099 100644
--- a/services/tests/servicestests/src/com/android/server/pm/PackageParserTest.java
+++ b/services/tests/servicestests/src/com/android/server/pm/PackageParserTest.java
@@ -31,7 +31,6 @@ import android.content.pm.ProviderInfo;
import android.content.pm.ServiceInfo;
import android.content.pm.SharedLibraryInfo;
import android.content.pm.Signature;
-import android.content.pm.UsesPermissionInfo;
import android.os.Bundle;
import android.os.Parcel;
import android.platform.test.annotations.Presubmit;
@@ -466,7 +465,6 @@ public class PackageParserTest {
pkg.services.add(new PackageParser.Service(dummy, new ServiceInfo()));
pkg.instrumentation.add(new PackageParser.Instrumentation(dummy, new InstrumentationInfo()));
pkg.requestedPermissions.add("foo7");
- pkg.usesPermissionInfos.add(new UsesPermissionInfo("foo7"));
pkg.implicitPermissions.add("foo25");
pkg.protectedBroadcasts = new ArrayList<>();
diff --git a/services/tests/servicestests/src/com/android/server/pm/dex/DexManagerTests.java b/services/tests/servicestests/src/com/android/server/pm/dex/DexManagerTests.java
index 2ddc71f570b8..48ab8d6698bd 100644
--- a/services/tests/servicestests/src/com/android/server/pm/dex/DexManagerTests.java
+++ b/services/tests/servicestests/src/com/android/server/pm/dex/DexManagerTests.java
@@ -141,7 +141,8 @@ public class DexManagerTests {
assertIsUsedByOtherApps(mBarUser0, pui, true);
assertTrue(pui.getDexUseInfoMap().isEmpty());
- assertHasDclInfo(mBarUser0, mFooUser0, mBarUser0.getBaseAndSplitDexPaths());
+ // A package loading another package's APK is not DCL (it's not app data).
+ assertNoDclInfo(mBarUser0);
}
@Test
@@ -334,7 +335,9 @@ public class DexManagerTests {
notifyDexLoad(mFooUser0, newSplits, mUser0);
PackageUseInfo pui = getPackageUseInfo(mBarUser0);
assertIsUsedByOtherApps(newSplits, pui, true);
- assertHasDclInfo(mBarUser0, mFooUser0, newSplits);
+
+ // Primary and split APKs are not recorded as DCL.
+ assertNoDclInfo(mBarUser0);
}
@Test
diff --git a/services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java b/services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java
index bfa0b74b6927..63341b6ea38a 100644
--- a/services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java
+++ b/services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java
@@ -150,7 +150,7 @@ public class PowerManagerServiceTest extends AndroidTestCase {
@SmallTest
public void testGetDesiredScreenPolicy_WithVR() throws Exception {
// Brighten up the screen
- mService.setWakefulnessLocked(WAKEFULNESS_AWAKE, 0);
+ mService.setWakefulnessLocked(WAKEFULNESS_AWAKE, PowerManager.WAKE_REASON_UNKNOWN, 0);
assertThat(mService.getDesiredScreenPolicyLocked()).isEqualTo(
DisplayPowerRequest.POLICY_BRIGHT);
@@ -160,12 +160,13 @@ public class PowerManagerServiceTest extends AndroidTestCase {
DisplayPowerRequest.POLICY_VR);
// Then take a nap
- mService.setWakefulnessLocked(WAKEFULNESS_ASLEEP, 0);
+ mService.setWakefulnessLocked(WAKEFULNESS_ASLEEP, PowerManager.GO_TO_SLEEP_REASON_TIMEOUT,
+ 0);
assertThat(mService.getDesiredScreenPolicyLocked()).isEqualTo(
DisplayPowerRequest.POLICY_OFF);
// Wake up to VR
- mService.setWakefulnessLocked(WAKEFULNESS_AWAKE, 0);
+ mService.setWakefulnessLocked(WAKEFULNESS_AWAKE, PowerManager.WAKE_REASON_UNKNOWN, 0);
assertThat(mService.getDesiredScreenPolicyLocked()).isEqualTo(
DisplayPowerRequest.POLICY_VR);
diff --git a/services/tests/wmtests/src/com/android/server/wm/ActivityMetricsLaunchObserverTests.java b/services/tests/wmtests/src/com/android/server/wm/ActivityMetricsLaunchObserverTests.java
index ee228610ab21..2de4ae02828c 100644
--- a/services/tests/wmtests/src/com/android/server/wm/ActivityMetricsLaunchObserverTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/ActivityMetricsLaunchObserverTests.java
@@ -57,7 +57,6 @@ import java.util.Arrays;
*/
@SmallTest
@Presubmit
-@FlakyTest(detail="promote once confirmed non-flaky")
public class ActivityMetricsLaunchObserverTests extends ActivityTestsBase {
private ActivityMetricsLogger mActivityMetricsLogger;
private ActivityMetricsLaunchObserver mLaunchObserver;
diff --git a/services/tests/wmtests/src/com/android/server/wm/AppChangeTransitionTests.java b/services/tests/wmtests/src/com/android/server/wm/AppChangeTransitionTests.java
index 3bf884face42..defe9811ebcf 100644
--- a/services/tests/wmtests/src/com/android/server/wm/AppChangeTransitionTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/AppChangeTransitionTests.java
@@ -42,7 +42,6 @@ import org.junit.Test;
* Build/Install/Run:
* atest WmTests:AppChangeTransitionTests
*/
-@FlakyTest(detail = "Promote when shown to be stable.")
@SmallTest
public class AppChangeTransitionTests extends WindowTestsBase {
diff --git a/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenAnimationTests.java b/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenAnimationTests.java
index ea5ab7bf0621..dd5f32d248b7 100644
--- a/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenAnimationTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenAnimationTests.java
@@ -87,8 +87,8 @@ public class AppWindowTokenAnimationTests extends WindowTestsBase {
verify(mSpec).startAnimation(any(), any(), callbackCaptor.capture());
callbackCaptor.getValue().onAnimationFinished(mSpec);
- verify(mTransaction).reparent(eq(leash), eq(null));
- verify(mTransaction).reparent(eq(animationBoundsLayer), eq(null));
+ verify(mTransaction).remove(eq(leash));
+ verify(mTransaction).remove(eq(animationBoundsLayer));
assertThat(mToken.mNeedsAnimationBoundsLayer).isFalse();
}
@@ -100,8 +100,8 @@ public class AppWindowTokenAnimationTests extends WindowTestsBase {
final SurfaceControl animationBoundsLayer = mToken.mAnimationBoundsLayer;
mToken.mSurfaceAnimator.cancelAnimation();
- verify(mTransaction).reparent(eq(leash), eq(null));
- verify(mTransaction).reparent(eq(animationBoundsLayer), eq(null));
+ verify(mTransaction).remove(eq(leash));
+ verify(mTransaction).remove(eq(animationBoundsLayer));
assertThat(mToken.mNeedsAnimationBoundsLayer).isFalse();
}
diff --git a/services/tests/wmtests/src/com/android/server/wm/DimmerTests.java b/services/tests/wmtests/src/com/android/server/wm/DimmerTests.java
index f99cd4b18647..5b32fe68feae 100644
--- a/services/tests/wmtests/src/com/android/server/wm/DimmerTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/DimmerTests.java
@@ -166,7 +166,7 @@ public class DimmerTests extends WindowTestsBase {
mDimmer.updateDims(mTransaction, new Rect());
verify(mTransaction).show(getDimLayer());
- verify(dimLayer, never()).destroy();
+ verify(dimLayer, never()).remove();
}
@Test
@@ -212,7 +212,7 @@ public class DimmerTests extends WindowTestsBase {
mDimmer.updateDims(mTransaction, new Rect());
verify(mSurfaceAnimatorStarter).startAnimation(any(SurfaceAnimator.class), any(
SurfaceControl.Transaction.class), any(AnimationAdapter.class), anyBoolean());
- verify(mHost.getPendingTransaction()).reparent(dimLayer, null);
+ verify(mHost.getPendingTransaction()).remove(dimLayer);
}
@Test
@@ -228,7 +228,7 @@ public class DimmerTests extends WindowTestsBase {
mDimmer.updateDims(mTransaction, new Rect());
verify(mTransaction).show(dimLayer);
- verify(dimLayer, never()).destroy();
+ verify(dimLayer, never()).remove();
}
@Test
@@ -269,7 +269,7 @@ public class DimmerTests extends WindowTestsBase {
mDimmer.updateDims(mTransaction, new Rect());
verify(mSurfaceAnimatorStarter, never()).startAnimation(any(SurfaceAnimator.class), any(
SurfaceControl.Transaction.class), any(AnimationAdapter.class), anyBoolean());
- verify(mTransaction).reparent(dimLayer, null);
+ verify(mTransaction).remove(dimLayer);
}
private SurfaceControl getDimLayer() {
diff --git a/services/tests/wmtests/src/com/android/server/wm/InsetsSourceProviderTest.java b/services/tests/wmtests/src/com/android/server/wm/InsetsSourceProviderTest.java
index a498a1a9172a..0c363de36328 100644
--- a/services/tests/wmtests/src/com/android/server/wm/InsetsSourceProviderTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/InsetsSourceProviderTest.java
@@ -39,7 +39,6 @@ import org.junit.Before;
import org.junit.Test;
@SmallTest
-@FlakyTest(detail = "Promote once confirmed non-flaky")
@Presubmit
public class InsetsSourceProviderTest extends WindowTestsBase {
diff --git a/services/tests/wmtests/src/com/android/server/wm/PendingRemoteAnimationRegistryTest.java b/services/tests/wmtests/src/com/android/server/wm/PendingRemoteAnimationRegistryTest.java
index beaac8e58686..86bf3dbb6973 100644
--- a/services/tests/wmtests/src/com/android/server/wm/PendingRemoteAnimationRegistryTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/PendingRemoteAnimationRegistryTest.java
@@ -40,7 +40,6 @@ import org.mockito.MockitoAnnotations;
* atest WmTests:PendingRemoteAnimationRegistryTest
*/
@SmallTest
-@FlakyTest
@Presubmit
public class PendingRemoteAnimationRegistryTest extends ActivityTestsBase {
diff --git a/services/tests/wmtests/src/com/android/server/wm/PersisterQueueTests.java b/services/tests/wmtests/src/com/android/server/wm/PersisterQueueTests.java
index 434ba932f8ad..c3d2f33b17dd 100644
--- a/services/tests/wmtests/src/com/android/server/wm/PersisterQueueTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/PersisterQueueTests.java
@@ -47,7 +47,6 @@ import java.util.function.Predicate;
* atest WmTests:PersisterQueueTests
*/
@MediumTest
-@FlakyTest(detail = "Confirm stable in post-submit before removing")
@Presubmit
public class PersisterQueueTests implements PersisterQueue.Listener {
private static final long INTER_WRITE_DELAY_MS = 50;
diff --git a/services/tests/wmtests/src/com/android/server/wm/SafeActivityOptionsTest.java b/services/tests/wmtests/src/com/android/server/wm/SafeActivityOptionsTest.java
index 530fd6d7d70e..dad6c952d7ab 100644
--- a/services/tests/wmtests/src/com/android/server/wm/SafeActivityOptionsTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/SafeActivityOptionsTest.java
@@ -31,7 +31,6 @@ import org.junit.Test;
* atest WmTests:SafeActivityOptionsTest
*/
@MediumTest
-@FlakyTest
@Presubmit
public class SafeActivityOptionsTest {
diff --git a/services/tests/wmtests/src/com/android/server/wm/SurfaceAnimatorTest.java b/services/tests/wmtests/src/com/android/server/wm/SurfaceAnimatorTest.java
index 9b84215a8f3b..8c32e8cea93c 100644
--- a/services/tests/wmtests/src/com/android/server/wm/SurfaceAnimatorTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/SurfaceAnimatorTest.java
@@ -96,7 +96,7 @@ public class SurfaceAnimatorTest extends WindowTestsBase {
callbackCaptor.getValue().onAnimationFinished(mSpec);
assertNotAnimating(mAnimatable);
assertTrue(mAnimatable.mFinishedCallbackCalled);
- verify(mTransaction).reparent(eq(mAnimatable.mLeash), eq(null));
+ verify(mTransaction).remove(eq(mAnimatable.mLeash));
// TODO: Verify reparenting once we use mPendingTransaction to reparent it back
}
@@ -106,7 +106,7 @@ public class SurfaceAnimatorTest extends WindowTestsBase {
final SurfaceControl firstLeash = mAnimatable.mLeash;
mAnimatable.mSurfaceAnimator.startAnimation(mTransaction, mSpec2, true /* hidden */);
- verify(mTransaction).reparent(eq(firstLeash), eq(null));
+ verify(mTransaction).remove(eq(firstLeash));
assertFalse(mAnimatable.mFinishedCallbackCalled);
final ArgumentCaptor<OnAnimationFinishedCallback> callbackCaptor = ArgumentCaptor.forClass(
@@ -133,7 +133,7 @@ public class SurfaceAnimatorTest extends WindowTestsBase {
assertNotAnimating(mAnimatable);
verify(mSpec).onAnimationCancelled(any());
assertTrue(mAnimatable.mFinishedCallbackCalled);
- verify(mTransaction).reparent(eq(mAnimatable.mLeash), eq(null));
+ verify(mTransaction).remove(eq(mAnimatable.mLeash));
}
@Test
@@ -155,7 +155,7 @@ public class SurfaceAnimatorTest extends WindowTestsBase {
verifyZeroInteractions(mSpec);
assertNotAnimating(mAnimatable);
assertTrue(mAnimatable.mFinishedCallbackCalled);
- verify(mTransaction).reparent(eq(mAnimatable.mLeash), eq(null));
+ verify(mTransaction).remove(eq(mAnimatable.mLeash));
}
@Test
@@ -171,15 +171,14 @@ public class SurfaceAnimatorTest extends WindowTestsBase {
assertNotAnimating(mAnimatable);
assertAnimating(mAnimatable2);
assertEquals(leash, mAnimatable2.mSurfaceAnimator.mLeash);
- verify(mTransaction, never()).reparent(eq(leash), eq(null));
+ verify(mTransaction, never()).remove(eq(leash));
callbackCaptor.getValue().onAnimationFinished(mSpec);
assertNotAnimating(mAnimatable2);
assertTrue(mAnimatable2.mFinishedCallbackCalled);
- verify(mTransaction).reparent(eq(leash), eq(null));
+ verify(mTransaction).remove(eq(leash));
}
@Test
- @FlakyTest(detail = "Promote once confirmed non-flaky")
public void testDeferFinish() {
// Start animation
@@ -198,7 +197,7 @@ public class SurfaceAnimatorTest extends WindowTestsBase {
mDeferFinishAnimatable.mEndDeferFinishCallback.run();
assertNotAnimating(mAnimatable2);
assertTrue(mDeferFinishAnimatable.mFinishedCallbackCalled);
- verify(mTransaction).reparent(eq(mDeferFinishAnimatable.mLeash), eq(null));
+ verify(mTransaction).remove(eq(mDeferFinishAnimatable.mLeash));
}
private void assertAnimating(MyAnimatable animatable) {
diff --git a/services/tests/wmtests/src/com/android/server/wm/TaskPersisterTest.java b/services/tests/wmtests/src/com/android/server/wm/TaskPersisterTest.java
index df7bc11663bc..12ed3c28161f 100644
--- a/services/tests/wmtests/src/com/android/server/wm/TaskPersisterTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/TaskPersisterTest.java
@@ -41,7 +41,6 @@ import org.junit.Test;
* Build/Install/Run:
* atest WmTests:TaskPersisterTest
*/
-@FlakyTest(detail = "Promote to presubmit if stable")
@Presubmit
public class TaskPersisterTest {
private static final String TEST_USER_NAME = "AM-Test-User";
diff --git a/services/tests/wmtests/src/com/android/server/wm/TestWindowManagerPolicy.java b/services/tests/wmtests/src/com/android/server/wm/TestWindowManagerPolicy.java
index d1fe48aa63cd..bfb9193551f2 100644
--- a/services/tests/wmtests/src/com/android/server/wm/TestWindowManagerPolicy.java
+++ b/services/tests/wmtests/src/com/android/server/wm/TestWindowManagerPolicy.java
@@ -28,6 +28,7 @@ import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.os.Bundle;
import android.os.IBinder;
+import android.os.PowerManager.WakeReason;
import android.os.RemoteException;
import android.util.proto.ProtoOutputStream;
import android.view.IWindow;
@@ -182,11 +183,11 @@ class TestWindowManagerPolicy implements WindowManagerPolicy {
}
@Override
- public void startedWakingUp() {
+ public void startedWakingUp(@WakeReason int reason) {
}
@Override
- public void finishedWakingUp() {
+ public void finishedWakingUp(@WakeReason int reason) {
}
@Override
diff --git a/services/tests/wmtests/src/com/android/server/wm/WindowContainerControllerTests.java b/services/tests/wmtests/src/com/android/server/wm/WindowContainerControllerTests.java
index de3567ed5018..af8ccc981bae 100644
--- a/services/tests/wmtests/src/com/android/server/wm/WindowContainerControllerTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/WindowContainerControllerTests.java
@@ -37,7 +37,6 @@ import org.junit.Test;
* Build/Install/Run:
* atest FrameworksServicesTests:WindowContainerControllerTests
*/
-@FlakyTest(bugId = 74078662)
@SmallTest
@Presubmit
public class WindowContainerControllerTests extends WindowTestsBase {
diff --git a/services/tests/wmtests/src/com/android/server/wm/WindowStateTests.java b/services/tests/wmtests/src/com/android/server/wm/WindowStateTests.java
index c09cd46a6c04..8876214b9636 100644
--- a/services/tests/wmtests/src/com/android/server/wm/WindowStateTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/WindowStateTests.java
@@ -21,6 +21,7 @@ import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
import static android.hardware.camera2.params.OutputConfiguration.ROTATION_90;
import static android.view.InsetsState.TYPE_TOP_BAR;
import static android.view.Surface.ROTATION_0;
+import static android.view.ViewRootImpl.NEW_INSETS_MODE_FULL;
import static android.view.WindowManager.LayoutParams.FIRST_SUB_WINDOW;
import static android.view.WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM;
import static android.view.WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
@@ -48,6 +49,7 @@ import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.anyLong;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
@@ -60,13 +62,15 @@ import android.util.Size;
import android.view.DisplayCutout;
import android.view.InsetsSource;
import android.view.SurfaceControl;
+import android.view.ViewRootImpl;
import android.view.WindowManager;
-import androidx.test.filters.FlakyTest;
import androidx.test.filters.SmallTest;
import com.android.server.wm.utils.WmDisplayCutout;
+import org.junit.AfterClass;
+import org.junit.BeforeClass;
import org.junit.Test;
import java.util.LinkedList;
@@ -77,10 +81,23 @@ import java.util.LinkedList;
* Build/Install/Run:
* atest FrameworksServicesTests:WindowStateTests
*/
-@FlakyTest(bugId = 74078662)
@SmallTest
@Presubmit
public class WindowStateTests extends WindowTestsBase {
+ private static int sPreviousNewInsetsMode;
+
+ @BeforeClass
+ public static void setUpOnce() {
+ sPreviousNewInsetsMode = ViewRootImpl.sNewInsetsMode;
+ // To let the insets provider control the insets visibility, the insets mode has to be
+ // NEW_INSETS_MODE_FULL.
+ ViewRootImpl.sNewInsetsMode = NEW_INSETS_MODE_FULL;
+ }
+
+ @AfterClass
+ public static void tearDownOnce() {
+ ViewRootImpl.sNewInsetsMode = sPreviousNewInsetsMode;
+ }
@Test
public void testIsParentWindowHidden() {
@@ -263,12 +280,12 @@ public class WindowStateTests extends WindowTestsBase {
reset(sPowerManagerWrapper);
first.prepareWindowToDisplayDuringRelayout(false /*wasVisible*/);
- verify(sPowerManagerWrapper, never()).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper, never()).wakeUp(anyLong(), anyInt(), anyString());
assertTrue(appWindowToken.canTurnScreenOn());
reset(sPowerManagerWrapper);
second.prepareWindowToDisplayDuringRelayout(false /*wasVisible*/);
- verify(sPowerManagerWrapper).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper).wakeUp(anyLong(), anyInt(), anyString());
assertFalse(appWindowToken.canTurnScreenOn());
// Call prepareWindowToDisplayDuringRelayout for two window that have FLAG_TURN_SCREEN_ON
@@ -279,12 +296,12 @@ public class WindowStateTests extends WindowTestsBase {
reset(sPowerManagerWrapper);
first.prepareWindowToDisplayDuringRelayout(false /*wasVisible*/);
- verify(sPowerManagerWrapper).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper).wakeUp(anyLong(), anyInt(), anyString());
assertFalse(appWindowToken.canTurnScreenOn());
reset(sPowerManagerWrapper);
second.prepareWindowToDisplayDuringRelayout(false /*wasVisible*/);
- verify(sPowerManagerWrapper, never()).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper, never()).wakeUp(anyLong(), anyInt(), anyString());
assertFalse(appWindowToken.canTurnScreenOn());
// Call prepareWindowToDisplayDuringRelayout for a windows that are not children of an
@@ -300,11 +317,11 @@ public class WindowStateTests extends WindowTestsBase {
reset(sPowerManagerWrapper);
firstWindow.prepareWindowToDisplayDuringRelayout(false /*wasVisible*/);
- verify(sPowerManagerWrapper).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper).wakeUp(anyLong(), anyInt(), anyString());
reset(sPowerManagerWrapper);
secondWindow.prepareWindowToDisplayDuringRelayout(false /*wasVisible*/);
- verify(sPowerManagerWrapper).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper).wakeUp(anyLong(), anyInt(), anyString());
}
@Test
@@ -435,6 +452,6 @@ public class WindowStateTests extends WindowTestsBase {
root.mAttrs.flags |= WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON;
root.prepareWindowToDisplayDuringRelayout(wasVisible /*wasVisible*/);
- verify(sPowerManagerWrapper).wakeUp(anyLong(), anyString());
+ verify(sPowerManagerWrapper).wakeUp(anyLong(), anyInt(), anyString());
}
}
diff --git a/services/tests/wmtests/src/com/android/server/wm/WindowTokenTests.java b/services/tests/wmtests/src/com/android/server/wm/WindowTokenTests.java
index 3048f1a3487b..d55688665f70 100644
--- a/services/tests/wmtests/src/com/android/server/wm/WindowTokenTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/WindowTokenTests.java
@@ -39,7 +39,6 @@ import org.junit.Test;
* Build/Install/Run:
* atest FrameworksServicesTests:WindowTokenTests
*/
-@FlakyTest(bugId = 74078662)
@SmallTest
@Presubmit
public class WindowTokenTests extends WindowTestsBase {
diff --git a/services/tests/wmtests/src/com/android/server/wm/WindowTracingTest.java b/services/tests/wmtests/src/com/android/server/wm/WindowTracingTest.java
index b81a8e72301a..b6b9a861a282 100644
--- a/services/tests/wmtests/src/com/android/server/wm/WindowTracingTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/WindowTracingTest.java
@@ -60,7 +60,6 @@ import java.nio.charset.StandardCharsets;
* Build/Install/Run:
* atest FrameworksServicesTests:WindowTracingTest
*/
-@FlakyTest(bugId = 74078662)
@SmallTest
@Presubmit
public class WindowTracingTest {
diff --git a/services/tests/wmtests/src/com/android/server/wm/utils/RotationCacheTest.java b/services/tests/wmtests/src/com/android/server/wm/utils/RotationCacheTest.java
index 33f34b465576..05d8237b4da4 100644
--- a/services/tests/wmtests/src/com/android/server/wm/utils/RotationCacheTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/utils/RotationCacheTest.java
@@ -37,7 +37,6 @@ import org.junit.Test;
* atest WmTests:RotationCacheTest
*/
@SmallTest
-@FlakyTest(bugId = 74078662)
@Presubmit
public class RotationCacheTest {
diff --git a/services/usage/java/com/android/server/usage/UsageStatsService.java b/services/usage/java/com/android/server/usage/UsageStatsService.java
index a6d7ee6d85e2..df2f45512465 100644
--- a/services/usage/java/com/android/server/usage/UsageStatsService.java
+++ b/services/usage/java/com/android/server/usage/UsageStatsService.java
@@ -493,6 +493,8 @@ public class UsageStatsService extends SystemService implements
switch (event.mEventType) {
case Event.ACTIVITY_RESUMED:
synchronized (mVisibleActivities) {
+ // check if this activity has already been resumed
+ if (mVisibleActivities.get(event.mInstanceId) != null) break;
mVisibleActivities.put(event.mInstanceId, event.getClassName());
try {
mAppTimeLimit.noteUsageStart(packageName, userId);
diff --git a/startop/view_compiler/OWNERS b/startop/view_compiler/OWNERS
new file mode 100644
index 000000000000..e5aead9ddac8
--- /dev/null
+++ b/startop/view_compiler/OWNERS
@@ -0,0 +1,2 @@
+eholk@google.com
+mathieuc@google.com
diff --git a/telephony/java/com/android/internal/telephony/cdma/SmsMessage.java b/telephony/java/com/android/internal/telephony/cdma/SmsMessage.java
index 964a31304db5..9080e23eb88f 100644
--- a/telephony/java/com/android/internal/telephony/cdma/SmsMessage.java
+++ b/telephony/java/com/android/internal/telephony/cdma/SmsMessage.java
@@ -21,7 +21,6 @@ import android.os.SystemProperties;
import android.telephony.PhoneNumberUtils;
import android.telephony.SmsCbLocation;
import android.telephony.SmsCbMessage;
-import android.telephony.TelephonyManager;
import android.telephony.cdma.CdmaSmsCbProgramData;
import android.telephony.Rlog;
import android.util.Log;
@@ -746,8 +745,10 @@ public class SmsMessage extends SmsMessageBase {
/**
* Parses a broadcast SMS, possibly containing a CMAS alert.
+ *
+ * @param plmn the PLMN for a broadcast SMS
*/
- public SmsCbMessage parseBroadcastSms() {
+ public SmsCbMessage parseBroadcastSms(String plmn) {
BearerData bData = BearerData.decode(mEnvelope.bearerData, mEnvelope.serviceCategory);
if (bData == null) {
Rlog.w(LOG_TAG, "BearerData.decode() returned null");
@@ -758,7 +759,6 @@ public class SmsMessage extends SmsMessageBase {
Rlog.d(LOG_TAG, "MT raw BearerData = " + HexDump.toHexString(mEnvelope.bearerData));
}
- String plmn = TelephonyManager.getDefault().getNetworkOperator();
SmsCbLocation location = new SmsCbLocation(plmn);
return new SmsCbMessage(SmsCbMessage.MESSAGE_FORMAT_3GPP2,
@@ -858,11 +858,11 @@ public class SmsMessage extends SmsMessageBase {
bearerData.userData = userData;
byte[] encodedBearerData = BearerData.encode(bearerData);
+ if (encodedBearerData == null) return null;
if (Rlog.isLoggable(LOGGABLE_TAG, Log.VERBOSE)) {
Rlog.d(LOG_TAG, "MO (encoded) BearerData = " + bearerData);
Rlog.d(LOG_TAG, "MO raw BearerData = '" + HexDump.toHexString(encodedBearerData) + "'");
}
- if (encodedBearerData == null) return null;
int teleservice = bearerData.hasUserDataHeader ?
SmsEnvelope.TELESERVICE_WEMT : SmsEnvelope.TELESERVICE_WMT;
diff --git a/tests/RollbackTest/src/com/android/tests/rollback/RollbackTest.java b/tests/RollbackTest/src/com/android/tests/rollback/RollbackTest.java
index 4b277ae850c5..f07ae9f65b1b 100644
--- a/tests/RollbackTest/src/com/android/tests/rollback/RollbackTest.java
+++ b/tests/RollbackTest/src/com/android/tests/rollback/RollbackTest.java
@@ -685,7 +685,7 @@ public class RollbackTest {
ActivityManager am = context.getSystemService(ActivityManager.class);
am.killBackgroundProcesses(TEST_APP_A);
// Allow another package launch
- crashQueue.offer(intent.getIntExtra("count", 0), 5, TimeUnit.SECONDS);
+ crashQueue.put(intent.getIntExtra("count", 0));
} catch (InterruptedException e) {
fail("Failed to communicate with test app");
}
@@ -694,14 +694,9 @@ public class RollbackTest {
context.registerReceiver(crashCountReceiver, crashCountFilter);
// Start apps PackageWatchdog#TRIGGER_FAILURE_COUNT times so TEST_APP_A crashes
- Integer crashCount = null;
do {
RollbackTestUtils.launchPackage(TEST_APP_A);
- crashCount = crashQueue.poll(5, TimeUnit.SECONDS);
- if (crashCount == null) {
- fail("Timed out waiting for crash signal from test app");
- }
- } while(crashCount < 5);
+ } while(crashQueue.take() < 5);
// TEST_APP_A is automatically rolled back by the RollbackPackageHealthObserver
assertEquals(1, RollbackTestUtils.getInstalledVersion(TEST_APP_A));
diff --git a/tools/stats_log_api_gen/Collation.cpp b/tools/stats_log_api_gen/Collation.cpp
index 257043b30704..a8d970edaa85 100644
--- a/tools/stats_log_api_gen/Collation.cpp
+++ b/tools/stats_log_api_gen/Collation.cpp
@@ -48,6 +48,7 @@ AtomDecl::AtomDecl(const AtomDecl& that)
primaryFields(that.primaryFields),
exclusiveField(that.exclusiveField),
uidField(that.uidField),
+ whitelisted(that.whitelisted),
binaryFields(that.binaryFields) {}
AtomDecl::AtomDecl(int c, const string& n, const string& m)
@@ -162,6 +163,7 @@ int collate_atom(const Descriptor *atom, AtomDecl *atomDecl,
vector<java_type_t> *signature) {
int errorCount = 0;
+
// Build a sorted list of the fields. Descriptor has them in source file
// order.
map<int, const FieldDescriptor *> fields;
@@ -387,6 +389,11 @@ int collate_atoms(const Descriptor *descriptor, Atoms *atoms) {
const Descriptor *atom = atomField->message_type();
AtomDecl atomDecl(atomField->number(), atomField->name(), atom->name());
+
+ if (atomField->options().GetExtension(os::statsd::allow_from_any_uid) == true) {
+ atomDecl.whitelisted = true;
+ }
+
vector<java_type_t> signature;
errorCount += collate_atom(atom, &atomDecl, &signature);
if (atomDecl.primaryFields.size() != 0 && atomDecl.exclusiveField == 0) {
diff --git a/tools/stats_log_api_gen/Collation.h b/tools/stats_log_api_gen/Collation.h
index 450b30547c21..6b86b862dfad 100644
--- a/tools/stats_log_api_gen/Collation.h
+++ b/tools/stats_log_api_gen/Collation.h
@@ -89,6 +89,8 @@ struct AtomDecl {
int uidField = 0;
+ bool whitelisted = false;
+
vector<int> binaryFields;
AtomDecl();
diff --git a/tools/stats_log_api_gen/main.cpp b/tools/stats_log_api_gen/main.cpp
index 4491a8567441..55440d2261d3 100644
--- a/tools/stats_log_api_gen/main.cpp
+++ b/tools/stats_log_api_gen/main.cpp
@@ -158,6 +158,20 @@ static int write_stats_log_cpp(FILE *out, const Atoms &atoms,
}
}
}
+
+ fprintf(out, "};\n");
+ fprintf(out, "\n");
+
+ fprintf(out,
+ "const std::set<int> AtomsInfo::kWhitelistedAtoms = {\n");
+ for (set<AtomDecl>::const_iterator atom = atoms.decls.begin();
+ atom != atoms.decls.end(); atom++) {
+ if (atom->whitelisted) {
+ string constant = make_constant_name(atom->name);
+ fprintf(out, " %s,\n", constant.c_str());
+ }
+ }
+
fprintf(out, "};\n");
fprintf(out, "\n");
@@ -728,6 +742,8 @@ write_stats_log_header(FILE* out, const Atoms& atoms, const AtomDecl &attributio
fprintf(out,
" const static std::map<int, std::vector<int>> "
"kBytesFieldAtoms;");
+ fprintf(out,
+ " const static std::set<int> kWhitelistedAtoms;\n");
fprintf(out, "};\n");
fprintf(out, "const static int kMaxPushedAtomId = %d;\n\n",
diff --git a/tools/stats_log_api_gen/test.proto b/tools/stats_log_api_gen/test.proto
index 3be87d95df15..24ebf4de031a 100644
--- a/tools/stats_log_api_gen/test.proto
+++ b/tools/stats_log_api_gen/test.proto
@@ -195,4 +195,22 @@ message GoodStateAtom3 {
[(android.os.statsd.state_field_option).option = PRIMARY];
optional int32 state = 3
[(android.os.statsd.state_field_option).option = EXCLUSIVE];
+}
+
+message WhitelistedAtom {
+ optional int32 field = 1;
+}
+
+message NonWhitelistedAtom {
+ optional int32 field = 1;
+}
+
+message ListedAtoms {
+ oneof event {
+ // Atoms can be whitelisted i.e. they can be triggered by any source
+ WhitelistedAtom whitelisted_atom = 1 [(android.os.statsd.allow_from_any_uid) = true];
+ // Atoms are not whitelisted by default, so they can only be triggered
+ // by whitelisted sources
+ NonWhitelistedAtom non_whitelisted_atom = 2;
+ }
} \ No newline at end of file
diff --git a/tools/stats_log_api_gen/test_collation.cpp b/tools/stats_log_api_gen/test_collation.cpp
index ad3bffacd442..dc585c1c5dd1 100644
--- a/tools/stats_log_api_gen/test_collation.cpp
+++ b/tools/stats_log_api_gen/test_collation.cpp
@@ -226,5 +226,25 @@ TEST(CollationTest, FailOnBadBinaryFieldAtom) {
EXPECT_TRUE(errorCount > 0);
}
+TEST(CollationTest, PassOnWhitelistedAtom) {
+ Atoms atoms;
+ int errorCount =
+ collate_atoms(ListedAtoms::descriptor(), &atoms);
+ EXPECT_EQ(errorCount, 0);
+ EXPECT_EQ(atoms.decls.size(), 2ul);
+}
+
+TEST(CollationTest, RecogniseWhitelistedAtom) {
+ Atoms atoms;
+ collate_atoms(ListedAtoms::descriptor(), &atoms);
+ for (const auto& atomDecl : atoms.decls) {
+ if (atomDecl.code == 1) {
+ EXPECT_TRUE(atomDecl.whitelisted);
+ } else {
+ EXPECT_FALSE(atomDecl.whitelisted);
+ }
+ }
+}
+
} // namespace stats_log_api_gen
} // namespace android \ No newline at end of file