diff options
113 files changed, 3392 insertions, 999 deletions
diff --git a/Android.bp b/Android.bp index 54fedaf9bb0f..9e65646154b8 100644 --- a/Android.bp +++ b/Android.bp @@ -503,7 +503,9 @@ filegroup { visibility: ["//visibility:private"], } -// These defaults are used for both the jar stubs and the doc stubs. +// Defaults for all stubs that include the non-updatable framework. These defaults do not include +// module symbols, so will not compile correctly on their own. Users must add module APIs to the +// classpath (or sources) somehow. stubs_defaults { name: "android-non-updatable-stubs-defaults", srcs: [":android-non-updatable-stub-sources"], @@ -511,17 +513,14 @@ stubs_defaults { system_modules: "none", java_version: "1.8", arg_files: ["core/res/AndroidManifest.xml"], - // TODO(b/147699819): remove below aidl includes. aidl: { local_include_dirs: [ - "apex/media/aidl/stable", "media/aidl", "telephony/java", ], include_dirs: [ "frameworks/av/aidl", "frameworks/native/libs/permission/aidl", - "packages/modules/Connectivity/framework/aidl-export", ], }, // These are libs from framework-internal-utils that are required (i.e. being referenced) @@ -543,6 +542,30 @@ stubs_defaults { "android.hardware.usb.gadget-V1.0-java", "android.hardware.vibrator-V1.3-java", "framework-protos", + ], + filter_packages: packages_to_document, + high_mem: true, // Lots of sources => high memory use, see b/170701554 + installable: false, + annotations_enabled: true, + previous_api: ":android.api.public.latest", + merge_annotations_dirs: ["metalava-manual"], + defaults_visibility: ["//visibility:private"], + visibility: ["//frameworks/base/api"], +} + +// Defaults with module APIs in the classpath (mostly from prebuilts). +// Suitable for compiling android-non-updatable. +stubs_defaults { + name: "module-classpath-stubs-defaults", + aidl: { + local_include_dirs: [ + "apex/media/aidl/stable", + ], + include_dirs: [ + "packages/modules/Connectivity/framework/aidl-export", + ], + }, + libs: [ "art.module.public.api", "sdk_module-lib_current_framework-tethering", // There are a few classes from modules used by the core that @@ -553,14 +576,7 @@ stubs_defaults { // NOTE: The below can be removed once the prebuilt stub contains IKE. "sdk_system_current_android.net.ipsec.ike", ], - filter_packages: packages_to_document, - high_mem: true, // Lots of sources => high memory use, see b/170701554 - installable: false, - annotations_enabled: true, - previous_api: ":android.api.public.latest", - merge_annotations_dirs: ["metalava-manual"], defaults_visibility: ["//visibility:private"], - visibility: ["//frameworks/base/api"], } build = [ diff --git a/ApiDocs.bp b/ApiDocs.bp index ec7b19482c82..f7bd34ea2d66 100644 --- a/ApiDocs.bp +++ b/ApiDocs.bp @@ -57,7 +57,10 @@ framework_docs_only_libs = [ stubs_defaults { name: "android-non-updatable-doc-stubs-defaults", - defaults: ["android-non-updatable-stubs-defaults"], + defaults: [ + "android-non-updatable-stubs-defaults", + "module-classpath-stubs-defaults", + ], srcs: [ // No longer part of the stubs, but are included in the docs. ":android-test-base-sources", @@ -71,39 +74,21 @@ stubs_defaults { stubs_defaults { name: "framework-doc-stubs-default", + defaults: ["android-non-updatable-stubs-defaults"], srcs: [ - ":android-non-updatable-stub-sources", - // No longer part of the stubs, but are included in the docs. ":android-test-base-sources", ":android-test-mock-sources", ":android-test-runner-sources", ], - arg_files: [ - "core/res/AndroidManifest.xml", - ], libs: framework_docs_only_libs, create_doc_stubs: true, - annotations_enabled: true, - filter_packages: packages_to_document, api_levels_annotations_enabled: true, api_levels_annotations_dirs: [ "sdk-dir", "api-versions-jars-dir", ], - previous_api: ":android.api.public.latest", - merge_annotations_dirs: [ - "metalava-manual", - ], write_sdk_values: true, - // TODO(b/169090544): remove below aidl includes. - aidl: { - local_include_dirs: ["media/aidl"], - include_dirs: [ - "frameworks/av/aidl", - "frameworks/native/libs/permission/aidl", - ], - }, } // Defaults module for doc-stubs targets that use module source code as input. diff --git a/StubLibraries.bp b/StubLibraries.bp index 2ce37921715e..9e8b7071d0c7 100644 --- a/StubLibraries.bp +++ b/StubLibraries.bp @@ -24,23 +24,15 @@ // with the latest frozen API signature. ///////////////////////////////////////////////////////////////////// -// Common metalava configs -///////////////////////////////////////////////////////////////////// - -stubs_defaults { - name: "metalava-non-updatable-api-stubs-default", - defaults: ["android-non-updatable-stubs-defaults"], - api_levels_annotations_enabled: false, - defaults_visibility: ["//visibility:private"], -} - -///////////////////////////////////////////////////////////////////// // These modules provide source files for the stub libraries ///////////////////////////////////////////////////////////////////// droidstubs { name: "api-stubs-docs-non-updatable", - defaults: ["metalava-non-updatable-api-stubs-default"], + defaults: [ + "android-non-updatable-stubs-defaults", + "module-classpath-stubs-defaults", + ], args: metalava_framework_docs_args, check_api: { current: { @@ -89,7 +81,10 @@ module_libs = " --show-annotation android.annotation.SystemApi\\(" + droidstubs { name: "system-api-stubs-docs-non-updatable", - defaults: ["metalava-non-updatable-api-stubs-default"], + defaults: [ + "android-non-updatable-stubs-defaults", + "module-classpath-stubs-defaults", + ], args: metalava_framework_docs_args + priv_apps, check_api: { current: { @@ -125,7 +120,10 @@ droidstubs { droidstubs { name: "test-api-stubs-docs-non-updatable", - defaults: ["metalava-non-updatable-api-stubs-default"], + defaults: [ + "android-non-updatable-stubs-defaults", + "module-classpath-stubs-defaults", + ], args: metalava_framework_docs_args + test + priv_apps_in_stubs, check_api: { current: { @@ -167,7 +165,10 @@ droidstubs { droidstubs { name: "module-lib-api-stubs-docs-non-updatable", - defaults: ["metalava-non-updatable-api-stubs-default"], + defaults: [ + "android-non-updatable-stubs-defaults", + "module-classpath-stubs-defaults", + ], args: metalava_framework_docs_args + priv_apps_in_stubs + module_libs, check_api: { current: { diff --git a/cmds/app_process/Android.bp b/cmds/app_process/Android.bp index a1575173ded6..6a685a79cc33 100644 --- a/cmds/app_process/Android.bp +++ b/cmds/app_process/Android.bp @@ -64,6 +64,8 @@ cc_binary { "libwilhelm", ], + header_libs: ["bionic_libc_platform_headers"], + compile_multilib: "both", cflags: [ diff --git a/cmds/app_process/app_main.cpp b/cmds/app_process/app_main.cpp index 12083b6fe20b..815f9455471c 100644 --- a/cmds/app_process/app_main.cpp +++ b/cmds/app_process/app_main.cpp @@ -15,6 +15,7 @@ #include <android-base/macros.h> #include <binder/IPCThreadState.h> +#include <bionic/pac.h> #include <hwbinder/IPCThreadState.h> #include <utils/Log.h> #include <cutils/memory.h> @@ -182,6 +183,10 @@ int main(int argc, char* const argv[]) ALOGV("app_process main with argv: %s", argv_String.string()); } + // Because of applications that are using PAC instructions incorrectly, PAC + // is disabled in application processes for now. + ScopedDisablePAC x; + AppRuntime runtime(argv[0], computeArgBlockSize(argc, argv)); // Process command line arguments // ignore argv[0] diff --git a/core/api/current.txt b/core/api/current.txt index 3550d327340d..add4158230db 100644 --- a/core/api/current.txt +++ b/core/api/current.txt @@ -7185,6 +7185,7 @@ package android.app.admin { method @Nullable public java.util.List<java.lang.String> getPermittedCrossProfileNotificationListeners(@NonNull android.content.ComponentName); method @Nullable public java.util.List<java.lang.String> getPermittedInputMethods(@NonNull android.content.ComponentName); method public int getPersonalAppsSuspendedReasons(@NonNull android.content.ComponentName); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig getPreferentialNetworkServiceConfig(); method public int getRequiredPasswordComplexity(); method public long getRequiredStrongAuthTimeout(@Nullable android.content.ComponentName); method public boolean getScreenCaptureDisabled(@Nullable android.content.ComponentName); @@ -7327,6 +7328,7 @@ package android.app.admin { method public boolean setPermittedCrossProfileNotificationListeners(@NonNull android.content.ComponentName, @Nullable java.util.List<java.lang.String>); method public boolean setPermittedInputMethods(@NonNull android.content.ComponentName, java.util.List<java.lang.String>); method public void setPersonalAppsSuspended(@NonNull android.content.ComponentName, boolean); + method public void setPreferentialNetworkServiceConfig(@NonNull android.app.admin.PreferentialNetworkServiceConfig); method public void setPreferentialNetworkServiceEnabled(boolean); method public void setProfileEnabled(@NonNull android.content.ComponentName); method public void setProfileName(@NonNull android.content.ComponentName, String); @@ -7572,6 +7574,32 @@ package android.app.admin { field @NonNull public static final android.os.Parcelable.Creator<android.app.admin.NetworkEvent> CREATOR; } + public final class PreferentialNetworkServiceConfig implements android.os.Parcelable { + method public int describeContents(); + method @NonNull public int[] getExcludedUids(); + method @NonNull public int[] getIncludedUids(); + method public int getNetworkId(); + method public boolean isEnabled(); + method public boolean isFallbackToDefaultConnectionAllowed(); + method public void writeToParcel(@NonNull android.os.Parcel, int); + field @NonNull public static final android.os.Parcelable.Creator<android.app.admin.PreferentialNetworkServiceConfig> CREATOR; + field public static final int PREFERENTIAL_NETWORK_ID_1 = 1; // 0x1 + field public static final int PREFERENTIAL_NETWORK_ID_2 = 2; // 0x2 + field public static final int PREFERENTIAL_NETWORK_ID_3 = 3; // 0x3 + field public static final int PREFERENTIAL_NETWORK_ID_4 = 4; // 0x4 + field public static final int PREFERENTIAL_NETWORK_ID_5 = 5; // 0x5 + } + + public static final class PreferentialNetworkServiceConfig.Builder { + ctor public PreferentialNetworkServiceConfig.Builder(); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig build(); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig.Builder setEnabled(boolean); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig.Builder setExcludedUids(@NonNull int[]); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig.Builder setFallbackToDefaultConnectionAllowed(boolean); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig.Builder setIncludedUids(@NonNull int[]); + method @NonNull public android.app.admin.PreferentialNetworkServiceConfig.Builder setNetworkId(int); + } + public class SecurityLog { ctor public SecurityLog(); field public static final int LEVEL_ERROR = 3; // 0x3 @@ -8642,6 +8670,7 @@ package android.bluetooth { method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public java.util.Set<android.bluetooth.BluetoothDevice> getBondedDevices(); method @Deprecated public static android.bluetooth.BluetoothAdapter getDefaultAdapter(); method public int getLeMaximumAdvertisingDataLength(); + method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public int getMaxConnectedAudioDevices(); method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public String getName(); method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public int getProfileConnectionState(int); method public boolean getProfileProxy(android.content.Context, android.bluetooth.BluetoothProfile.ServiceListener, int); @@ -8652,11 +8681,12 @@ package android.bluetooth { method @RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN) public boolean isDiscovering(); method public boolean isEnabled(); method public boolean isLe2MPhySupported(); + method public int isLeAudioBroadcastAssistantSupported(); + method public int isLeAudioBroadcastSourceSupported(); method public int isLeAudioSupported(); method public boolean isLeCodedPhySupported(); method public boolean isLeExtendedAdvertisingSupported(); method public boolean isLePeriodicAdvertisingSupported(); - method public int isLePeriodicAdvertisingSyncTransferSenderSupported(); method public boolean isMultipleAdvertisementSupported(); method public boolean isOffloadedFilteringSupported(); method public boolean isOffloadedScanBatchingSupported(); @@ -9154,6 +9184,7 @@ package android.bluetooth { field public static final String EXTRA_PAIRING_VARIANT = "android.bluetooth.device.extra.PAIRING_VARIANT"; field public static final String EXTRA_PREVIOUS_BOND_STATE = "android.bluetooth.device.extra.PREVIOUS_BOND_STATE"; field public static final String EXTRA_RSSI = "android.bluetooth.device.extra.RSSI"; + field public static final String EXTRA_TRANSPORT = "android.bluetooth.device.extra.TRANSPORT"; field public static final String EXTRA_UUID = "android.bluetooth.device.extra.UUID"; field public static final int PAIRING_VARIANT_PASSKEY_CONFIRMATION = 2; // 0x2 field public static final int PAIRING_VARIANT_PIN = 0; // 0x0 @@ -9516,24 +9547,61 @@ package android.bluetooth { method public void close(); method protected void finalize(); method @NonNull @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public java.util.List<android.bluetooth.BluetoothDevice> getConnectedDevices(); + method @Nullable @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public android.bluetooth.BluetoothDevice getConnectedGroupLeadDevice(int); method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public int getConnectionState(@NonNull android.bluetooth.BluetoothDevice); method @NonNull @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public java.util.List<android.bluetooth.BluetoothDevice> getDevicesMatchingConnectionStates(@NonNull int[]); method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public int getGroupId(@NonNull android.bluetooth.BluetoothDevice); field @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public static final String ACTION_LE_AUDIO_CONNECTION_STATE_CHANGED = "android.bluetooth.action.LE_AUDIO_CONNECTION_STATE_CHANGED"; } - public final class BluetoothLeAudioCodecConfig { + public final class BluetoothLeAudioCodecConfig implements android.os.Parcelable { + method public int describeContents(); + method public int getBitsPerSample(); + method public int getChannelMode(); method @NonNull public String getCodecName(); + method public int getCodecPriority(); method public int getCodecType(); + method public int getFrameDuration(); method public static int getMaxCodecType(); + method public int getOctetsPerFrame(); + method public int getSampleRate(); + method public void writeToParcel(@NonNull android.os.Parcel, int); + field public static final int BITS_PER_SAMPLE_16 = 1; // 0x1 + field public static final int BITS_PER_SAMPLE_24 = 2; // 0x2 + field public static final int BITS_PER_SAMPLE_32 = 3; // 0x3 + field public static final int BITS_PER_SAMPLE_NONE = 0; // 0x0 + field public static final int CHANNEL_MODE_MONO = 1; // 0x1 + field public static final int CHANNEL_MODE_NONE = 0; // 0x0 + field public static final int CHANNEL_MODE_STEREO = 2; // 0x2 + field public static final int CODEC_PRIORITY_DEFAULT = 0; // 0x0 + field public static final int CODEC_PRIORITY_DISABLED = -1; // 0xffffffff + field public static final int CODEC_PRIORITY_HIGHEST = 1000000; // 0xf4240 + field @NonNull public static final android.os.Parcelable.Creator<android.bluetooth.BluetoothLeAudioCodecConfig> CREATOR; + field public static final int FRAME_DURATION_10000 = 2; // 0x2 + field public static final int FRAME_DURATION_7500 = 1; // 0x1 + field public static final int FRAME_DURATION_NONE = 0; // 0x0 + field public static final int SAMPLE_RATE_16000 = 2; // 0x2 + field public static final int SAMPLE_RATE_24000 = 3; // 0x3 + field public static final int SAMPLE_RATE_32000 = 4; // 0x4 + field public static final int SAMPLE_RATE_44100 = 5; // 0x5 + field public static final int SAMPLE_RATE_48000 = 6; // 0x6 + field public static final int SAMPLE_RATE_8000 = 1; // 0x1 + field public static final int SAMPLE_RATE_NONE = 0; // 0x0 field public static final int SOURCE_CODEC_TYPE_INVALID = 1000000; // 0xf4240 field public static final int SOURCE_CODEC_TYPE_LC3 = 0; // 0x0 } public static final class BluetoothLeAudioCodecConfig.Builder { ctor public BluetoothLeAudioCodecConfig.Builder(); + ctor public BluetoothLeAudioCodecConfig.Builder(@NonNull android.bluetooth.BluetoothLeAudioCodecConfig); method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig build(); + method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setBitsPerSample(int); + method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setChannelMode(int); + method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setCodecPriority(int); method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setCodecType(int); + method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setFrameDuration(int); + method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setOctetsPerFrame(int); + method @NonNull public android.bluetooth.BluetoothLeAudioCodecConfig.Builder setSampleRate(int); } public final class BluetoothManager { @@ -9554,6 +9622,7 @@ package android.bluetooth { field public static final String EXTRA_STATE = "android.bluetooth.profile.extra.STATE"; field public static final int GATT = 7; // 0x7 field public static final int GATT_SERVER = 8; // 0x8 + field public static final int HAP_CLIENT = 28; // 0x1c field public static final int HEADSET = 1; // 0x1 field @Deprecated public static final int HEALTH = 3; // 0x3 field public static final int HEARING_AID = 21; // 0x15 @@ -21882,9 +21951,11 @@ package android.media { field public static final int COLOR_Format24bitBGR888 = 12; // 0xc field @Deprecated public static final int COLOR_Format24bitRGB888 = 11; // 0xb field @Deprecated public static final int COLOR_Format25bitARGB1888 = 14; // 0xe + field public static final int COLOR_Format32bitABGR2101010 = 2130750114; // 0x7f00aaa2 field public static final int COLOR_Format32bitABGR8888 = 2130747392; // 0x7f00a000 field @Deprecated public static final int COLOR_Format32bitARGB8888 = 16; // 0x10 field @Deprecated public static final int COLOR_Format32bitBGRA8888 = 15; // 0xf + field public static final int COLOR_Format64bitABGRFloat = 2130710294; // 0x7f000f16 field @Deprecated public static final int COLOR_Format8bitRGB332 = 2; // 0x2 field @Deprecated public static final int COLOR_FormatCbYCrY = 27; // 0x1b field @Deprecated public static final int COLOR_FormatCrYCbY = 28; // 0x1c @@ -21917,10 +21988,12 @@ package android.media { field @Deprecated public static final int COLOR_FormatYUV422SemiPlanar = 24; // 0x18 field public static final int COLOR_FormatYUV444Flexible = 2135181448; // 0x7f444888 field @Deprecated public static final int COLOR_FormatYUV444Interleaved = 29; // 0x1d + field public static final int COLOR_FormatYUVP010 = 54; // 0x36 field @Deprecated public static final int COLOR_QCOM_FormatYUV420SemiPlanar = 2141391872; // 0x7fa30c00 field @Deprecated public static final int COLOR_TI_FormatYUV420PackedSemiPlanar = 2130706688; // 0x7f000100 field public static final String FEATURE_AdaptivePlayback = "adaptive-playback"; field public static final String FEATURE_DynamicTimestamp = "dynamic-timestamp"; + field public static final String FEATURE_EncodingStatistics = "encoding-statistics"; field public static final String FEATURE_FrameParsing = "frame-parsing"; field public static final String FEATURE_IntraRefresh = "intra-refresh"; field public static final String FEATURE_LowLatency = "low-latency"; @@ -22694,6 +22767,7 @@ package android.media { field public static final String KEY_OPERATING_RATE = "operating-rate"; field public static final String KEY_OUTPUT_REORDER_DEPTH = "output-reorder-depth"; field public static final String KEY_PCM_ENCODING = "pcm-encoding"; + field public static final String KEY_PICTURE_TYPE = "picture-type"; field public static final String KEY_PIXEL_ASPECT_RATIO_HEIGHT = "sar-height"; field public static final String KEY_PIXEL_ASPECT_RATIO_WIDTH = "sar-width"; field public static final String KEY_PREPEND_HEADER_TO_SYNC_FRAMES = "prepend-sps-pps-to-idr-frames"; @@ -22711,6 +22785,8 @@ package android.media { field public static final String KEY_TILE_HEIGHT = "tile-height"; field public static final String KEY_TILE_WIDTH = "tile-width"; field public static final String KEY_TRACK_ID = "track-id"; + field public static final String KEY_VIDEO_ENCODING_STATISTICS_LEVEL = "video-encoding-statistics-level"; + field public static final String KEY_VIDEO_QP_AVERAGE = "video-qp-average"; field public static final String KEY_VIDEO_QP_B_MAX = "video-qp-b-max"; field public static final String KEY_VIDEO_QP_B_MIN = "video-qp-b-min"; field public static final String KEY_VIDEO_QP_I_MAX = "video-qp-i-max"; @@ -22755,12 +22831,18 @@ package android.media { field public static final String MIMETYPE_VIDEO_SCRAMBLED = "video/scrambled"; field public static final String MIMETYPE_VIDEO_VP8 = "video/x-vnd.on2.vp8"; field public static final String MIMETYPE_VIDEO_VP9 = "video/x-vnd.on2.vp9"; + field public static final int PICTURE_TYPE_B = 3; // 0x3 + field public static final int PICTURE_TYPE_I = 1; // 0x1 + field public static final int PICTURE_TYPE_P = 2; // 0x2 + field public static final int PICTURE_TYPE_UNKNOWN = 0; // 0x0 field public static final int TYPE_BYTE_BUFFER = 5; // 0x5 field public static final int TYPE_FLOAT = 3; // 0x3 field public static final int TYPE_INTEGER = 1; // 0x1 field public static final int TYPE_LONG = 2; // 0x2 field public static final int TYPE_NULL = 0; // 0x0 field public static final int TYPE_STRING = 4; // 0x4 + field public static final int VIDEO_ENCODING_STATISTICS_LEVEL_1 = 1; // 0x1 + field public static final int VIDEO_ENCODING_STATISTICS_LEVEL_NONE = 0; // 0x0 } public final class MediaMetadata implements android.os.Parcelable { @@ -31589,7 +31671,7 @@ package android.os { method @Deprecated public void readMap(@NonNull java.util.Map, @Nullable ClassLoader); method public <K, V> void readMap(@NonNull java.util.Map<? super K,? super V>, @Nullable ClassLoader, @NonNull Class<K>, @NonNull Class<V>); method @Deprecated @Nullable public <T extends android.os.Parcelable> T readParcelable(@Nullable ClassLoader); - method @Nullable public <T> T readParcelable(@Nullable ClassLoader, @NonNull Class<T>); + method @Nullable public <T extends android.os.Parcelable> T readParcelable(@Nullable ClassLoader, @NonNull Class<? super T>); method @Deprecated @Nullable public android.os.Parcelable[] readParcelableArray(@Nullable ClassLoader); method @Nullable public <T> T[] readParcelableArray(@Nullable ClassLoader, @NonNull Class<T>); method @Deprecated @Nullable public android.os.Parcelable.Creator<?> readParcelableCreator(@Nullable ClassLoader); @@ -31599,7 +31681,7 @@ package android.os { method @Nullable public android.os.PersistableBundle readPersistableBundle(); method @Nullable public android.os.PersistableBundle readPersistableBundle(@Nullable ClassLoader); method @Deprecated @Nullable public java.io.Serializable readSerializable(); - method @Nullable public <T> T readSerializable(@Nullable ClassLoader, @NonNull Class<T>); + method @Nullable public <T extends java.io.Serializable> T readSerializable(@Nullable ClassLoader, @NonNull Class<? super T>); method @NonNull public android.util.Size readSize(); method @NonNull public android.util.SizeF readSizeF(); method @Deprecated @Nullable public <T> android.util.SparseArray<T> readSparseArray(@Nullable ClassLoader); @@ -41291,6 +41373,7 @@ package android.telephony { field public static final String KEY_SUPPORTED_IKE_SESSION_ENCRYPTION_ALGORITHMS_INT_ARRAY = "iwlan.supported_ike_session_encryption_algorithms_int_array"; field public static final String KEY_SUPPORTED_INTEGRITY_ALGORITHMS_INT_ARRAY = "iwlan.supported_integrity_algorithms_int_array"; field public static final String KEY_SUPPORTED_PRF_ALGORITHMS_INT_ARRAY = "iwlan.supported_prf_algorithms_int_array"; + field public static final String KEY_SUPPORTS_EAP_AKA_FAST_REAUTH_BOOL = "iwlan.supports_eap_aka_fast_reauth_bool"; } public abstract class CellIdentity implements android.os.Parcelable { diff --git a/core/api/module-lib-current.txt b/core/api/module-lib-current.txt index ff187815cbd0..74ec189514c5 100644 --- a/core/api/module-lib-current.txt +++ b/core/api/module-lib-current.txt @@ -56,12 +56,30 @@ package android.app.usage { public class NetworkStatsManager { method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK}) public void forceUpdate(); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK}) public void notifyNetworkStatus(@NonNull java.util.List<android.net.Network>, @NonNull java.util.List<android.net.NetworkStateSnapshot>, @Nullable String, @NonNull java.util.List<android.net.UnderlyingNetworkInfo>); + method @NonNull @WorkerThread public android.app.usage.NetworkStats queryDetailsForDevice(@NonNull android.net.NetworkTemplate, long, long); + method @NonNull @WorkerThread public android.app.usage.NetworkStats queryDetailsForUidTagState(@NonNull android.net.NetworkTemplate, long, long, int, int, int) throws java.lang.SecurityException; + method @NonNull @WorkerThread public android.app.usage.NetworkStats querySummary(@NonNull android.net.NetworkTemplate, long, long) throws java.lang.SecurityException; + method @NonNull @WorkerThread public android.app.usage.NetworkStats.Bucket querySummaryForDevice(@NonNull android.net.NetworkTemplate, long, long); + method @NonNull @WorkerThread public android.app.usage.NetworkStats queryTaggedSummary(@NonNull android.net.NetworkTemplate, long, long) throws java.lang.SecurityException; + method public void registerUsageCallback(@NonNull android.net.NetworkTemplate, long, @NonNull java.util.concurrent.Executor, @NonNull android.app.usage.NetworkStatsManager.UsageCallback); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK}) public void setDefaultGlobalAlert(long); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK}) public void setPollOnOpen(boolean); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK}) public void setStatsProviderWarningAndLimitAsync(@NonNull String, long, long); method @RequiresPermission(anyOf={android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK, android.Manifest.permission.NETWORK_STACK}) public void setUidForeground(int, boolean); } + public abstract static class NetworkStatsManager.UsageCallback { + method public void onThresholdReached(@NonNull android.net.NetworkTemplate); + } + +} + +package android.bluetooth { + + public final class BluetoothPan implements android.bluetooth.BluetoothProfile { + method @Nullable @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED, android.Manifest.permission.TETHER_PRIVILEGED}) public android.net.TetheringManager.TetheredInterfaceRequest requestTetheredInterface(@NonNull java.util.concurrent.Executor, @NonNull android.net.TetheringManager.TetheredInterfaceCallback); + } + } package android.content { @@ -222,6 +240,36 @@ package android.net { method public int getResourceId(); } + public class LocalSocket implements java.io.Closeable { + ctor public LocalSocket(@NonNull java.io.FileDescriptor); + } + + public class NetworkIdentity { + method public int getOemManaged(); + method public int getRatType(); + method @Nullable public String getSubscriberId(); + method public int getType(); + method @Nullable public String getWifiNetworkKey(); + method public boolean isDefaultNetwork(); + method public boolean isMetered(); + method public boolean isRoaming(); + } + + public static final class NetworkIdentity.Builder { + ctor public NetworkIdentity.Builder(); + method @NonNull public android.net.NetworkIdentity build(); + method @NonNull public android.net.NetworkIdentity.Builder clearRatType(); + method @NonNull public android.net.NetworkIdentity.Builder setDefaultNetwork(boolean); + method @NonNull public android.net.NetworkIdentity.Builder setMetered(boolean); + method @NonNull public android.net.NetworkIdentity.Builder setNetworkStateSnapshot(@NonNull android.net.NetworkStateSnapshot); + method @NonNull public android.net.NetworkIdentity.Builder setOemManaged(int); + method @NonNull public android.net.NetworkIdentity.Builder setRatType(int); + method @NonNull public android.net.NetworkIdentity.Builder setRoaming(boolean); + method @NonNull public android.net.NetworkIdentity.Builder setSubscriberId(@Nullable String); + method @NonNull public android.net.NetworkIdentity.Builder setType(int); + method @NonNull public android.net.NetworkIdentity.Builder setWifiNetworkKey(@Nullable String); + } + public class NetworkPolicyManager { method @RequiresPermission(android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) public int getMultipathPreference(@NonNull android.net.Network); method @RequiresPermission(android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) public int getRestrictBackgroundStatus(int); @@ -249,6 +297,44 @@ package android.net { field @NonNull public static final android.os.Parcelable.Creator<android.net.NetworkStateSnapshot> CREATOR; } + public class NetworkStatsCollection { + method @NonNull public java.util.Map<android.net.NetworkStatsCollection.Key,android.net.NetworkStatsHistory> getEntries(); + } + + public static final class NetworkStatsCollection.Builder { + ctor public NetworkStatsCollection.Builder(long); + method @NonNull public android.net.NetworkStatsCollection.Builder addEntry(@NonNull android.net.NetworkStatsCollection.Key, @NonNull android.net.NetworkStatsHistory); + method @NonNull public android.net.NetworkStatsCollection build(); + } + + public static class NetworkStatsCollection.Key { + ctor public NetworkStatsCollection.Key(@NonNull java.util.Set<android.net.NetworkIdentity>, int, int, int); + } + + public final class NetworkStatsHistory implements android.os.Parcelable { + method public int describeContents(); + method @NonNull public java.util.List<android.net.NetworkStatsHistory.Entry> getEntries(); + method public void writeToParcel(@NonNull android.os.Parcel, int); + field @NonNull public static final android.os.Parcelable.Creator<android.net.NetworkStatsHistory> CREATOR; + } + + public static final class NetworkStatsHistory.Builder { + ctor public NetworkStatsHistory.Builder(long, int); + method @NonNull public android.net.NetworkStatsHistory.Builder addEntry(@NonNull android.net.NetworkStatsHistory.Entry); + method @NonNull public android.net.NetworkStatsHistory build(); + } + + public static final class NetworkStatsHistory.Entry { + ctor public NetworkStatsHistory.Entry(long, long, long, long, long, long, long); + method public long getActiveTime(); + method public long getBucketStart(); + method public long getOperations(); + method public long getRxBytes(); + method public long getRxPackets(); + method public long getTxBytes(); + method public long getTxPackets(); + } + public final class NetworkTemplate implements android.os.Parcelable { method public int describeContents(); method public int getDefaultNetworkStatus(); @@ -259,6 +345,7 @@ package android.net { method public int getRoaming(); method @NonNull public java.util.Set<java.lang.String> getSubscriberIds(); method @NonNull public java.util.Set<java.lang.String> getWifiNetworkKeys(); + method public boolean matches(@NonNull android.net.NetworkIdentity); method public void writeToParcel(@NonNull android.os.Parcel, int); field @NonNull public static final android.os.Parcelable.Creator<android.net.NetworkTemplate> CREATOR; field public static final int MATCH_BLUETOOTH = 8; // 0x8 @@ -304,6 +391,11 @@ package android.net { method public static void setHttpProxyConfiguration(@Nullable android.net.ProxyInfo); } + public class TrafficStats { + method public static void attachSocketTagger(); + method public static void init(@NonNull android.content.Context); + } + public final class UnderlyingNetworkInfo implements android.os.Parcelable { ctor public UnderlyingNetworkInfo(int, @NonNull String, @NonNull java.util.List<java.lang.String>); method public int describeContents(); @@ -379,6 +471,16 @@ package android.os { method @NonNull public java.util.List<android.content.ComponentName> getEnabledComponentOverrides(@NonNull String); } + public final class Trace { + method public static void asyncTraceBegin(long, @NonNull String, int); + method public static void asyncTraceEnd(long, @NonNull String, int); + method public static boolean isTagEnabled(long); + method public static void traceBegin(long, @NonNull String); + method public static void traceCounter(long, @NonNull String, int); + method public static void traceEnd(long); + field public static final long TRACE_TAG_NETWORK = 2097152L; // 0x200000L + } + } package android.os.storage { diff --git a/core/api/system-current.txt b/core/api/system-current.txt index 3f7fc3fde287..9e061d5878b9 100644 --- a/core/api/system-current.txt +++ b/core/api/system-current.txt @@ -316,6 +316,7 @@ package android { public static final class R.array { field public static final int config_keySystemUuidMapping = 17235973; // 0x1070005 + field public static final int config_optionalIpSecAlgorithms; } public static final class R.attr { @@ -1850,6 +1851,8 @@ package android.app.usage { } public class NetworkStatsManager { + method @NonNull @RequiresPermission(android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) public android.net.NetworkStats getMobileUidStats(); + method @NonNull @RequiresPermission(android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) public android.net.NetworkStats getWifiUidStats(); method @NonNull @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_STATS_PROVIDER, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void registerNetworkStatsProvider(@NonNull String, @NonNull android.net.netstats.provider.NetworkStatsProvider); method @NonNull @RequiresPermission(anyOf={android.Manifest.permission.NETWORK_STATS_PROVIDER, android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK}) public void unregisterNetworkStatsProvider(@NonNull android.net.netstats.provider.NetworkStatsProvider); } @@ -2015,6 +2018,7 @@ package android.bluetooth { method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public boolean isEncrypted(); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean isInSilenceMode(); method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public boolean removeBond(); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setLowLatencyAudioAllowed(boolean); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setMessageAccessPermission(int); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setMetadata(int, @NonNull byte[]); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setPhonebookAccessPermission(int); @@ -2024,9 +2028,11 @@ package android.bluetooth { field public static final int ACCESS_REJECTED = 2; // 0x2 field public static final int ACCESS_UNKNOWN = 0; // 0x0 field @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public static final String ACTION_SILENCE_MODE_CHANGED = "android.bluetooth.device.action.SILENCE_MODE_CHANGED"; + field @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public static final String ACTION_SWITCH_BUFFER_SIZE = "android.bluetooth.device.action.SWITCH_BUFFER_SIZE"; field public static final String DEVICE_TYPE_DEFAULT = "Default"; field public static final String DEVICE_TYPE_UNTETHERED_HEADSET = "Untethered Headset"; field public static final String DEVICE_TYPE_WATCH = "Watch"; + field public static final String EXTRA_LOW_LATENCY_BUFFER_SIZE = "android.bluetooth.device.extra.LOW_LATENCY_BUFFER_SIZE"; field public static final int METADATA_COMPANION_APP = 4; // 0x4 field public static final int METADATA_DEVICE_TYPE = 17; // 0x11 field public static final int METADATA_ENHANCED_SETTINGS_UI_URI = 16; // 0x10 @@ -2064,6 +2070,15 @@ package android.bluetooth { method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.MODIFY_PHONE_STATE}) public boolean stopScoUsingVirtualVoiceCall(); } + public final class BluetoothHeadsetClient implements java.lang.AutoCloseable android.bluetooth.BluetoothProfile { + method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getConnectedDevices(); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionState(@NonNull android.bluetooth.BluetoothDevice); + method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getDevicesMatchingConnectionStates(@NonNull int[]); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice, int); + field @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.headsetprofile.action.CONNECTION_STATE_CHANGED"; + } + public final class BluetoothHearingAid implements android.bluetooth.BluetoothProfile { method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public long getHiSyncId(@NonNull android.bluetooth.BluetoothDevice); @@ -2082,6 +2097,10 @@ package android.bluetooth { field @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.input.profile.action.CONNECTION_STATE_CHANGED"; } + public final class BluetoothLeAudio implements java.lang.AutoCloseable android.bluetooth.BluetoothProfile { + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getAudioLocation(@NonNull android.bluetooth.BluetoothDevice); + } + public final class BluetoothMap implements java.lang.AutoCloseable android.bluetooth.BluetoothProfile { method public void close(); method protected void finalize(); @@ -2091,15 +2110,21 @@ package android.bluetooth { field @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.map.profile.action.CONNECTION_STATE_CHANGED"; } - public final class BluetoothMapClient implements android.bluetooth.BluetoothProfile { + public final class BluetoothMapClient implements java.lang.AutoCloseable android.bluetooth.BluetoothProfile { + method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getConnectedDevices(); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionState(@NonNull android.bluetooth.BluetoothDevice); + method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getDevicesMatchingConnectionStates(@NonNull int[]); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.SEND_SMS}) public boolean sendMessage(@NonNull android.bluetooth.BluetoothDevice, @NonNull java.util.Collection<android.net.Uri>, @NonNull String, @Nullable android.app.PendingIntent, @Nullable android.app.PendingIntent); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice, int); + field @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.mapmce.profile.action.CONNECTION_STATE_CHANGED"; } public final class BluetoothPan implements android.bluetooth.BluetoothProfile { method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getConnectedDevices(); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionState(@NonNull android.bluetooth.BluetoothDevice); method @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public boolean isTetheringOn(); - method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED, android.Manifest.permission.TETHER_PRIVILEGED}) public void setBluetoothTethering(boolean); + method @Deprecated @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED, android.Manifest.permission.TETHER_PRIVILEGED}) public void setBluetoothTethering(boolean); method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice, int); field @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.pan.profile.action.CONNECTION_STATE_CHANGED"; field public static final String ACTION_TETHERING_STATE_CHANGED = "android.bluetooth.action.TETHERING_STATE_CHANGED"; @@ -2120,6 +2145,15 @@ package android.bluetooth { field @RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.pbap.profile.action.CONNECTION_STATE_CHANGED"; } + public final class BluetoothPbapClient implements java.lang.AutoCloseable android.bluetooth.BluetoothProfile { + method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getConnectedDevices(); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public int getConnectionState(@NonNull android.bluetooth.BluetoothDevice); + method @NonNull @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public java.util.List<android.bluetooth.BluetoothDevice> getDevicesMatchingConnectionStates(@NonNull int[]); + method @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public boolean setConnectionPolicy(@NonNull android.bluetooth.BluetoothDevice, int); + field @RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED}) public static final String ACTION_CONNECTION_STATE_CHANGED = "android.bluetooth.pbapclient.profile.action.CONNECTION_STATE_CHANGED"; + } + public interface BluetoothProfile { field public static final int A2DP_SINK = 11; // 0xb field public static final int AVRCP_CONTROLLER = 12; // 0xc @@ -2153,6 +2187,7 @@ package android.bluetooth { field @NonNull public static final android.os.ParcelUuid COORDINATED_SET; field @NonNull public static final android.os.ParcelUuid DIP; field @NonNull public static final android.os.ParcelUuid GENERIC_MEDIA_CONTROL; + field @NonNull public static final android.os.ParcelUuid HAS; field @NonNull public static final android.os.ParcelUuid HEARING_AID; field @NonNull public static final android.os.ParcelUuid HFP; field @NonNull public static final android.os.ParcelUuid HFP_AG; @@ -12326,6 +12361,7 @@ package android.telephony { } public static class TelephonyManager.ModemActivityInfoException extends java.lang.Exception { + ctor public TelephonyManager.ModemActivityInfoException(int); method public int getErrorCode(); field public static final int ERROR_INVALID_INFO_RECEIVED = 2; // 0x2 field public static final int ERROR_MODEM_RESPONSE_ERROR = 3; // 0x3 @@ -13692,6 +13728,7 @@ package android.telephony.ims { field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_3G = 6; // 0x6 field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_EHRPD = 4; // 0x4 field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_HSPAPLUS = 5; // 0x5 + field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_INTERNET_PDN = 12; // 0xc field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_IWLAN = 9; // 0x9 field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_LTE_VOPS_DISABLED = 2; // 0x2 field public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_LTE_VOPS_ENABLED = 3; // 0x3 diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java index 3b0a5f3e9bdd..6d7835f84dc7 100644 --- a/core/java/android/app/ActivityThread.java +++ b/core/java/android/app/ActivityThread.java @@ -97,6 +97,7 @@ import android.media.MediaFrameworkPlatformInitializer; import android.media.MediaServiceManager; import android.net.ConnectivityManager; import android.net.Proxy; +import android.net.TrafficStats; import android.net.Uri; import android.os.AsyncTask; import android.os.Binder; @@ -6663,6 +6664,13 @@ public final class ActivityThread extends ClientTransactionHandler NetworkSecurityConfigProvider.install(appContext); Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); + // For backward compatibility, TrafficStats needs static access to the application context. + // But for isolated apps which cannot access network related services, service discovery + // is restricted. Hence, calling this would result in NPE. + if (!Process.isIsolated()) { + TrafficStats.init(appContext); + } + // Continue loading instrumentation. if (ii != null) { initInstrumentation(ii, data, appContext); diff --git a/core/java/android/app/admin/DevicePolicyManager.java b/core/java/android/app/admin/DevicePolicyManager.java index 0fe80c45ad2a..3840f760eda8 100644 --- a/core/java/android/app/admin/DevicePolicyManager.java +++ b/core/java/android/app/admin/DevicePolicyManager.java @@ -10177,6 +10177,9 @@ public class DevicePolicyManager { * On fully-managed devices this method is unsupported because all traffic is considered * work traffic. * + * <p> This method enables preferential network service with a default configuration. + * To fine-tune the configuration, use {@link #setPreferentialNetworkServiceConfig) instead. + * * <p>This method can only be called by the profile owner of a managed profile. * @param enabled whether preferential network service should be enabled. * @throws SecurityException if the caller is not the profile owner. @@ -10215,6 +10218,56 @@ public class DevicePolicyManager { } /** + * Sets preferential network configuration on the work profile. + * {@see PreferentialNetworkServiceConfig} + * + * An example of a supported preferential network service is the Enterprise + * slice on 5G networks. + * + * By default, preferential network service is disabled on the work profile on supported + * carriers and devices. Admins can explicitly enable it with this API. + * On fully-managed devices this method is unsupported because all traffic is considered + * work traffic. + * + * <p>This method can only be called by the profile owner of a managed profile. + * @param preferentialNetworkServiceConfig preferential network configuration. + * @throws SecurityException if the caller is not the profile owner. + **/ + public void setPreferentialNetworkServiceConfig( + @NonNull PreferentialNetworkServiceConfig preferentialNetworkServiceConfig) { + throwIfParentInstance("setPreferentialNetworkServiceConfig"); + if (mService == null) { + return; + } + try { + mService.setPreferentialNetworkServiceConfig(preferentialNetworkServiceConfig); + } catch (RemoteException e) { + throw e.rethrowFromSystemServer(); + } + } + + /** + * Get preferential network configuration + * {@see PreferentialNetworkServiceConfig} + * + * <p>This method can be called by the profile owner of a managed profile. + * + * @return preferential network configuration. + * @throws SecurityException if the caller is not the profile owner. + */ + public @NonNull PreferentialNetworkServiceConfig getPreferentialNetworkServiceConfig() { + throwIfParentInstance("getPreferentialNetworkServiceConfig"); + if (mService == null) { + return PreferentialNetworkServiceConfig.DEFAULT; + } + try { + return mService.getPreferentialNetworkServiceConfig(); + } catch (RemoteException e) { + throw e.rethrowFromSystemServer(); + } + } + + /** * This method is mostly deprecated. * Most of the settings that still have an effect have dedicated setter methods or user * restrictions. See individual settings for details. diff --git a/core/java/android/app/admin/IDevicePolicyManager.aidl b/core/java/android/app/admin/IDevicePolicyManager.aidl index d287437b143b..c78a5a00f645 100644 --- a/core/java/android/app/admin/IDevicePolicyManager.aidl +++ b/core/java/android/app/admin/IDevicePolicyManager.aidl @@ -21,6 +21,7 @@ import android.app.admin.NetworkEvent; import android.app.IApplicationThread; import android.app.IServiceConnection; import android.app.admin.ParcelableGranteeMap; +import android.app.admin.PreferentialNetworkServiceConfig; import android.app.admin.StartInstallingUpdateCallback; import android.app.admin.SystemUpdateInfo; import android.app.admin.SystemUpdatePolicy; @@ -278,6 +279,10 @@ interface IDevicePolicyManager { void setPreferentialNetworkServiceEnabled(in boolean enabled); boolean isPreferentialNetworkServiceEnabled(int userHandle); + void setPreferentialNetworkServiceConfig( + in PreferentialNetworkServiceConfig preferentialNetworkServiceConfig); + PreferentialNetworkServiceConfig getPreferentialNetworkServiceConfig(); + void setLockTaskPackages(in ComponentName who, in String[] packages); String[] getLockTaskPackages(in ComponentName who); boolean isLockTaskPermitted(in String pkg); diff --git a/core/java/android/app/admin/PreferentialNetworkServiceConfig.aidl b/core/java/android/app/admin/PreferentialNetworkServiceConfig.aidl new file mode 100644 index 000000000000..6b6ee7d8d538 --- /dev/null +++ b/core/java/android/app/admin/PreferentialNetworkServiceConfig.aidl @@ -0,0 +1,20 @@ +/* +** +** Copyright 2022, 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.app.admin; + +parcelable PreferentialNetworkServiceConfig;
\ No newline at end of file diff --git a/core/java/android/app/admin/PreferentialNetworkServiceConfig.java b/core/java/android/app/admin/PreferentialNetworkServiceConfig.java new file mode 100644 index 000000000000..2849139c606b --- /dev/null +++ b/core/java/android/app/admin/PreferentialNetworkServiceConfig.java @@ -0,0 +1,335 @@ +/* + * Copyright (C) 2022 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.app.admin; + +import android.annotation.IntDef; +import android.annotation.NonNull; +import android.annotation.SuppressLint; +import android.os.Parcel; +import android.os.Parcelable; + +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.util.Objects; + +/** + * Network configuration to be set for the user profile + * {@see DevicePolicyManager#setPreferentialNetworkServiceConfig}. + */ +public final class PreferentialNetworkServiceConfig implements Parcelable { + final boolean mIsEnabled; + final int mNetworkId; + final boolean mAllowFallbackToDefaultConnection; + final int[] mIncludedUids; + final int[] mExcludedUids; + + /** @hide */ + public static final PreferentialNetworkServiceConfig DEFAULT = + (new PreferentialNetworkServiceConfig.Builder()).build(); + + /** + * Preferential network identifier 1. + */ + public static final int PREFERENTIAL_NETWORK_ID_1 = 1; + + /** + * Preferential network identifier 2. + */ + public static final int PREFERENTIAL_NETWORK_ID_2 = 2; + + /** + * Preferential network identifier 3. + */ + public static final int PREFERENTIAL_NETWORK_ID_3 = 3; + + /** + * Preferential network identifier 4. + */ + public static final int PREFERENTIAL_NETWORK_ID_4 = 4; + + /** + * Preferential network identifier 5. + */ + public static final int PREFERENTIAL_NETWORK_ID_5 = 5; + + /** @hide */ + @Retention(RetentionPolicy.SOURCE) + @IntDef(prefix = { "PREFERENTIAL_NETWORK_ID_" }, value = { + PREFERENTIAL_NETWORK_ID_1, + PREFERENTIAL_NETWORK_ID_2, + PREFERENTIAL_NETWORK_ID_3, + PREFERENTIAL_NETWORK_ID_4, + PREFERENTIAL_NETWORK_ID_5, + }) + + public @interface PreferentialNetworkPreferenceId { + } + + private PreferentialNetworkServiceConfig(boolean isEnabled, + boolean allowFallbackToDefaultConnection, int[] includedUids, + int[] excludedUids, @PreferentialNetworkPreferenceId int networkId) { + mIsEnabled = isEnabled; + mAllowFallbackToDefaultConnection = allowFallbackToDefaultConnection; + mIncludedUids = includedUids; + mExcludedUids = excludedUids; + mNetworkId = networkId; + } + + private PreferentialNetworkServiceConfig(Parcel in) { + mIsEnabled = in.readBoolean(); + mAllowFallbackToDefaultConnection = in.readBoolean(); + mNetworkId = in.readInt(); + mIncludedUids = in.createIntArray(); + mExcludedUids = in.createIntArray(); + } + + /** + * Is the preferential network enabled. + * @return true if enabled else false + */ + public boolean isEnabled() { + return mIsEnabled; + } + + /** + * is fallback to default network allowed. This boolean configures whether default connection + * (default internet or wifi) should be used or not if a preferential network service + * connection is not available. + * @return true if fallback is allowed, else false. + */ + public boolean isFallbackToDefaultConnectionAllowed() { + return mAllowFallbackToDefaultConnection; + } + + /** + * Get the array of uids that are applicable for the profile preference. + * + * {@see #getExcludedUids()} + * Included UIDs and Excluded UIDs can't both be non-empty. + * if both are empty, it means this request applies to all uids in the user profile. + * if included is not empty, then only included UIDs are applied. + * if excluded is not empty, then it is all uids in the user profile except these UIDs. + * @return Array of uids applicable for the profile preference. + * Empty array would mean that this request applies to all uids in the profile. + */ + public @NonNull int[] getIncludedUids() { + return mIncludedUids; + } + + /** + * Get the array of uids that are excluded for the profile preference. + * + * {@see #getIncludedUids()} + * Included UIDs and Excluded UIDs can't both be non-empty. + * if both are empty, it means this request applies to all uids in the user profile. + * if included is not empty, then only included UIDs are applied. + * if excluded is not empty, then it is all uids in the user profile except these UIDs. + * @return Array of uids that are excluded for the profile preference. + * Empty array would mean that this request applies to all uids in the profile. + */ + public @NonNull int[] getExcludedUids() { + return mExcludedUids; + } + + /** + * @return preference enterprise identifier. + * valid values starts from + * {@link #PREFERENTIAL_NETWORK_ID_1} to {@link #PREFERENTIAL_NETWORK_ID_5}. + * preference identifier is applicable only if preference network service is enabled + * + */ + public @PreferentialNetworkPreferenceId int getNetworkId() { + return mNetworkId; + } + + @Override + public String toString() { + return "PreferentialNetworkServiceConfig{" + + "mIsEnabled=" + isEnabled() + + "mAllowFallbackToDefaultConnection=" + isFallbackToDefaultConnectionAllowed() + + "mIncludedUids=" + mIncludedUids.toString() + + "mExcludedUids=" + mExcludedUids.toString() + + "mNetworkId=" + mNetworkId + + '}'; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + final PreferentialNetworkServiceConfig that = (PreferentialNetworkServiceConfig) o; + return mIsEnabled == that.mIsEnabled + && mAllowFallbackToDefaultConnection == that.mAllowFallbackToDefaultConnection + && mNetworkId == that.mNetworkId + && Objects.equals(mIncludedUids, that.mIncludedUids) + && Objects.equals(mExcludedUids, that.mExcludedUids); + } + + @Override + public int hashCode() { + return ((Objects.hashCode(mIsEnabled) * 17) + + (Objects.hashCode(mAllowFallbackToDefaultConnection) * 19) + + (Objects.hashCode(mIncludedUids) * 23) + + (Objects.hashCode(mExcludedUids) * 29) + + mNetworkId * 31); + } + + /** + * Builder used to create {@link PreferentialNetworkServiceConfig} objects. + * Specify the preferred Network preference + */ + public static final class Builder { + boolean mIsEnabled = false; + int mNetworkId = 0; + boolean mAllowFallbackToDefaultConnection = true; + int[] mIncludedUids = new int[0]; + int[] mExcludedUids = new int[0]; + + /** + * Constructs an empty Builder with preferential network disabled by default. + */ + public Builder() {} + + /** + * Set the preferential network service enabled state. + * Default value is false. + * @param isEnabled the desired network preference to use, true to enable else false + * @return The builder to facilitate chaining. + */ + @NonNull + public PreferentialNetworkServiceConfig.Builder setEnabled(boolean isEnabled) { + mIsEnabled = isEnabled; + return this; + } + + /** + * Set whether the default connection should be used as fallback. + * This boolean configures whether the default connection (default internet or wifi) + * should be used if a preferential network service connection is not available. + * Default value is true + * @param allowFallbackToDefaultConnection true if fallback is allowed else false + * @return The builder to facilitate chaining. + */ + @NonNull + @SuppressLint("MissingGetterMatchingBuilder") + public PreferentialNetworkServiceConfig.Builder setFallbackToDefaultConnectionAllowed( + boolean allowFallbackToDefaultConnection) { + mAllowFallbackToDefaultConnection = allowFallbackToDefaultConnection; + return this; + } + + /** + * Set the array of uids whose network access will go through this preferential + * network service. + * {@see #setExcludedUids(int[])} + * Included UIDs and Excluded UIDs can't both be non-empty. + * if both are empty, it means this request applies to all uids in the user profile. + * if included is not empty, then only included UIDs are applied. + * if excluded is not empty, then it is all uids in the user profile except these UIDs. + * @param uids array of included uids + * @return The builder to facilitate chaining. + */ + @NonNull + public PreferentialNetworkServiceConfig.Builder setIncludedUids( + @NonNull int[] uids) { + Objects.requireNonNull(uids); + mIncludedUids = uids; + return this; + } + + /** + * Set the array of uids who are not allowed through this preferential + * network service. + * {@see #setIncludedUids(int[])} + * Included UIDs and Excluded UIDs can't both be non-empty. + * if both are empty, it means this request applies to all uids in the user profile. + * if included is not empty, then only included UIDs are applied. + * if excluded is not empty, then it is all uids in the user profile except these UIDs. + * @param uids array of excluded uids + * @return The builder to facilitate chaining. + */ + @NonNull + public PreferentialNetworkServiceConfig.Builder setExcludedUids( + @NonNull int[] uids) { + Objects.requireNonNull(uids); + mExcludedUids = uids; + return this; + } + + /** + * Returns an instance of {@link PreferentialNetworkServiceConfig} created from the + * fields set on this builder. + */ + @NonNull + public PreferentialNetworkServiceConfig build() { + if (mIncludedUids.length > 0 && mExcludedUids.length > 0) { + throw new IllegalStateException("Both includedUids and excludedUids " + + "cannot be nonempty"); + } + return new PreferentialNetworkServiceConfig(mIsEnabled, + mAllowFallbackToDefaultConnection, mIncludedUids, mExcludedUids, mNetworkId); + } + + /** + * Set the preferential network identifier. + * Valid values starts from {@link #PREFERENTIAL_NETWORK_ID_1} to + * {@link #PREFERENTIAL_NETWORK_ID_5}. + * preference identifier is applicable only if preferential network service is enabled. + * @param preferenceId preference Id + * @return The builder to facilitate chaining. + */ + @NonNull + public PreferentialNetworkServiceConfig.Builder setNetworkId( + @PreferentialNetworkPreferenceId int preferenceId) { + if ((preferenceId < PREFERENTIAL_NETWORK_ID_1) + || (preferenceId > PREFERENTIAL_NETWORK_ID_5)) { + throw new IllegalArgumentException("Invalid preference identifier"); + } + mNetworkId = preferenceId; + return this; + } + } + + @Override + public void writeToParcel(@NonNull android.os.Parcel dest, int flags) { + dest.writeBoolean(mIsEnabled); + dest.writeBoolean(mAllowFallbackToDefaultConnection); + dest.writeInt(mNetworkId); + dest.writeIntArray(mIncludedUids); + dest.writeIntArray(mExcludedUids); + } + + @Override + public int describeContents() { + return 0; + } + + @NonNull + public static final Creator<PreferentialNetworkServiceConfig> CREATOR = + new Creator<PreferentialNetworkServiceConfig>() { + @Override + public PreferentialNetworkServiceConfig[] newArray(int size) { + return new PreferentialNetworkServiceConfig[size]; + } + + @Override + public PreferentialNetworkServiceConfig createFromParcel( + @NonNull android.os.Parcel in) { + return new PreferentialNetworkServiceConfig(in); + } + }; +} diff --git a/core/java/android/app/wallpapereffectsgeneration/OWNERS b/core/java/android/app/wallpapereffectsgeneration/OWNERS new file mode 100644 index 000000000000..2bc01541a939 --- /dev/null +++ b/core/java/android/app/wallpapereffectsgeneration/OWNERS @@ -0,0 +1,5 @@ +susharon@google.com +shanh@google.com +huiwu@google.com +srazdan@google.com + diff --git a/core/java/android/net/LocalServerSocket.java b/core/java/android/net/LocalServerSocket.java index d1f49d2082f5..506cbcb0623d 100644 --- a/core/java/android/net/LocalServerSocket.java +++ b/core/java/android/net/LocalServerSocket.java @@ -55,7 +55,9 @@ public class LocalServerSocket implements Closeable { * Create a LocalServerSocket from a file descriptor that's already * been created and bound. listen() will be called immediately on it. * Used for cases where file descriptors are passed in via environment - * variables + * variables. The passed-in FileDescriptor is not managed by this class + * and must be closed by the caller. Calling {@link #close()} on a socket + * created by this method has no effect. * * @param fd bound file descriptor * @throws IOException diff --git a/core/java/android/net/LocalSocket.java b/core/java/android/net/LocalSocket.java index 5b38f78782a8..b69410cf7d73 100644 --- a/core/java/android/net/LocalSocket.java +++ b/core/java/android/net/LocalSocket.java @@ -16,7 +16,14 @@ package android.net; +import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; + +import android.annotation.NonNull; +import android.annotation.SuppressLint; +import android.annotation.SystemApi; import android.compat.annotation.UnsupportedAppUsage; +import android.system.ErrnoException; +import android.system.Os; import java.io.Closeable; import java.io.FileDescriptor; @@ -74,32 +81,39 @@ public class LocalSocket implements Closeable { this.isBound = false; } + private void checkConnected() { + try { + Os.getpeername(impl.getFileDescriptor()); + } catch (ErrnoException e) { + throw new IllegalArgumentException("Not a connected socket", e); + } + isConnected = true; + isBound = true; + implCreated = true; + } + /** - * Creates a LocalSocket instances using the FileDescriptor for an already-connected - * AF_LOCAL/UNIX domain stream socket. Note: the FileDescriptor must be closed by the caller: - * closing the LocalSocket will not close it. + * Creates a LocalSocket instance using the {@link FileDescriptor} for an already-connected + * AF_LOCAL/UNIX domain stream socket. The passed-in FileDescriptor is not managed by this class + * and must be closed by the caller. Calling {@link #close()} on a socket created by this + * method has no effect. + * + * @param fd the filedescriptor to adopt * - * @hide - used by BluetoothSocket. + * @hide */ - public static LocalSocket createConnectedLocalSocket(FileDescriptor fd) { - return createConnectedLocalSocket(new LocalSocketImpl(fd), SOCKET_UNKNOWN); + @SystemApi(client = MODULE_LIBRARIES) + public LocalSocket(@NonNull @SuppressLint("UseParcelFileDescriptor") FileDescriptor fd) { + this(new LocalSocketImpl(fd), SOCKET_UNKNOWN); + checkConnected(); } /** * for use with LocalServerSocket.accept() */ static LocalSocket createLocalSocketForAccept(LocalSocketImpl impl) { - return createConnectedLocalSocket(impl, SOCKET_UNKNOWN); - } - - /** - * Creates a LocalSocket from an existing LocalSocketImpl that is already connected. - */ - private static LocalSocket createConnectedLocalSocket(LocalSocketImpl impl, int sockType) { - LocalSocket socket = new LocalSocket(impl, sockType); - socket.isConnected = true; - socket.isBound = true; - socket.implCreated = true; + LocalSocket socket = new LocalSocket(impl, SOCKET_UNKNOWN); + socket.checkConnected(); return socket; } diff --git a/core/java/android/net/vcn/VcnGatewayConnectionConfig.java b/core/java/android/net/vcn/VcnGatewayConnectionConfig.java index a6830b708c31..2339656979b5 100644 --- a/core/java/android/net/vcn/VcnGatewayConnectionConfig.java +++ b/core/java/android/net/vcn/VcnGatewayConnectionConfig.java @@ -549,8 +549,8 @@ public final class VcnGatewayConnectionConfig { * networks, a network will be chosen arbitrarily amongst the networks matching the highest * priority rule. * - * <p>If all networks fail to match the rules provided, an underlying network will still be - * selected (at random if necessary). + * <p>If all networks fail to match the rules provided, a carrier-owned underlying network + * will still be selected (if available, at random if necessary). * * @param underlyingNetworkTemplates a list of unique VcnUnderlyingNetworkTemplates that are * ordered from most to least preferred, or an empty list to use the default diff --git a/core/java/android/os/BatteryUsageStats.java b/core/java/android/os/BatteryUsageStats.java index 0f94cbef3886..86e6db1dc625 100644 --- a/core/java/android/os/BatteryUsageStats.java +++ b/core/java/android/os/BatteryUsageStats.java @@ -127,6 +127,7 @@ public final class BatteryUsageStats implements Parcelable { private final AggregateBatteryConsumer[] mAggregateBatteryConsumers; private final Parcel mHistoryBuffer; private final List<BatteryStats.HistoryTag> mHistoryTagPool; + private final BatteryStatsHistory mBatteryStatsHistory; private BatteryUsageStats(@NonNull Builder builder) { mStatsStartTimestampMs = builder.mStatsStartTimestampMs; @@ -138,6 +139,7 @@ public final class BatteryUsageStats implements Parcelable { mDischargedPowerUpperBound = builder.mDischargedPowerUpperBoundMah; mHistoryBuffer = builder.mHistoryBuffer; mHistoryTagPool = builder.mHistoryTagPool; + mBatteryStatsHistory = builder.mBatteryStatsHistory; mBatteryTimeRemainingMs = builder.mBatteryTimeRemainingMs; mChargeTimeRemainingMs = builder.mChargeTimeRemainingMs; mCustomPowerComponentNames = builder.mCustomPowerComponentNames; @@ -289,8 +291,8 @@ public final class BatteryUsageStats implements Parcelable { throw new IllegalStateException( "Battery history was not requested in the BatteryUsageStatsQuery"); } - return new BatteryStatsHistoryIterator(new BatteryStatsHistory(mHistoryBuffer), - mHistoryTagPool); + + return new BatteryStatsHistoryIterator(mBatteryStatsHistory, mHistoryTagPool); } @Override @@ -356,7 +358,10 @@ public final class BatteryUsageStats implements Parcelable { tag.poolIdx = source.readInt(); mHistoryTagPool.add(tag); } + mBatteryStatsHistory = new BatteryStatsHistory(mHistoryBuffer); + mBatteryStatsHistory.readFromBatteryUsageStatsParcel(source); } else { + mBatteryStatsHistory = null; mHistoryBuffer = null; mHistoryTagPool = null; } @@ -404,6 +409,7 @@ public final class BatteryUsageStats implements Parcelable { dest.writeInt(tag.uid); dest.writeInt(tag.poolIdx); } + mBatteryStatsHistory.writeToBatteryUsageStatsParcel(dest); } else { dest.writeBoolean(false); } @@ -757,6 +763,7 @@ public final class BatteryUsageStats implements Parcelable { new SparseArray<>(); private Parcel mHistoryBuffer; private List<BatteryStats.HistoryTag> mHistoryTagPool; + private BatteryStatsHistory mBatteryStatsHistory; public Builder(@NonNull String[] customPowerComponentNames) { this(customPowerComponentNames, false); @@ -865,10 +872,12 @@ public final class BatteryUsageStats implements Parcelable { * Sets the parceled recent history. */ @NonNull - public Builder setBatteryHistory(Parcel historyBuffer, - List<BatteryStats.HistoryTag> historyTagPool) { + public Builder setBatteryHistory(@NonNull Parcel historyBuffer, + @NonNull List<BatteryStats.HistoryTag> historyTagPool, + @NonNull BatteryStatsHistory batteryStatsHistory) { mHistoryBuffer = historyBuffer; mHistoryTagPool = historyTagPool; + mBatteryStatsHistory = batteryStatsHistory; return this; } diff --git a/core/java/android/os/Parcel.java b/core/java/android/os/Parcel.java index 09eac79c991e..ffaff9533c8c 100644 --- a/core/java/android/os/Parcel.java +++ b/core/java/android/os/Parcel.java @@ -3704,10 +3704,10 @@ public final class Parcel { final int m = list.size(); int i = 0; for (; i < m && i < n; i++) { - list.set(i, (T) readParcelableInternal(cl, clazz)); + list.set(i, readParcelableInternal(cl, clazz)); } for (; i < n; i++) { - list.add((T) readParcelableInternal(cl, clazz)); + list.add(readParcelableInternal(cl, clazz)); } for (; i < m; i++) { list.remove(n); @@ -4210,7 +4210,8 @@ public final class Parcel { * trying to instantiate an element. */ @Nullable - public <T> T readParcelable(@Nullable ClassLoader loader, @NonNull Class<T> clazz) { + public <T extends Parcelable> T readParcelable(@Nullable ClassLoader loader, + @NonNull Class<? super T> clazz) { Objects.requireNonNull(clazz); return readParcelableInternal(loader, clazz); } @@ -4220,7 +4221,8 @@ public final class Parcel { */ @SuppressWarnings("unchecked") @Nullable - private <T> T readParcelableInternal(@Nullable ClassLoader loader, @Nullable Class<T> clazz) { + private <T extends Parcelable> T readParcelableInternal(@Nullable ClassLoader loader, + @Nullable Class<? super T> clazz) { Parcelable.Creator<?> creator = readParcelableCreatorInternal(loader, clazz); if (creator == null) { return null; @@ -4456,7 +4458,8 @@ public final class Parcel { * deserializing the object. */ @Nullable - public <T> T readSerializable(@Nullable ClassLoader loader, @NonNull Class<T> clazz) { + public <T extends Serializable> T readSerializable(@Nullable ClassLoader loader, + @NonNull Class<? super T> clazz) { Objects.requireNonNull(clazz); return readSerializableInternal( loader == null ? getClass().getClassLoader() : loader, clazz); @@ -4466,8 +4469,8 @@ public final class Parcel { * @param clazz The type of the serializable expected or {@code null} for performing no checks */ @Nullable - private <T> T readSerializableInternal(@Nullable final ClassLoader loader, - @Nullable Class<T> clazz) { + private <T extends Serializable> T readSerializableInternal(@Nullable final ClassLoader loader, + @Nullable Class<? super T> clazz) { String name = readString(); if (name == null) { // For some reason we were unable to read the name of the Serializable (either there diff --git a/core/java/android/os/Trace.java b/core/java/android/os/Trace.java index d974e0c0713a..6b869f13059d 100644 --- a/core/java/android/os/Trace.java +++ b/core/java/android/os/Trace.java @@ -16,7 +16,10 @@ package android.os; +import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; + import android.annotation.NonNull; +import android.annotation.SystemApi; import android.compat.annotation.UnsupportedAppUsage; import dalvik.annotation.optimization.CriticalNative; @@ -90,6 +93,7 @@ public final class Trace { /** @hide */ public static final long TRACE_TAG_DATABASE = 1L << 20; /** @hide */ + @SystemApi(client = MODULE_LIBRARIES) public static final long TRACE_TAG_NETWORK = 1L << 21; /** @hide */ public static final long TRACE_TAG_ADB = 1L << 22; @@ -148,6 +152,7 @@ public final class Trace { * @hide */ @UnsupportedAppUsage + @SystemApi(client = MODULE_LIBRARIES) public static boolean isTagEnabled(long traceTag) { long tags = nativeGetEnabledTags(); return (tags & traceTag) != 0; @@ -163,7 +168,8 @@ public final class Trace { * @hide */ @UnsupportedAppUsage - public static void traceCounter(long traceTag, String counterName, int counterValue) { + @SystemApi(client = MODULE_LIBRARIES) + public static void traceCounter(long traceTag, @NonNull String counterName, int counterValue) { if (isTagEnabled(traceTag)) { nativeTraceCounter(traceTag, counterName, counterValue); } @@ -202,7 +208,8 @@ public final class Trace { * @hide */ @UnsupportedAppUsage - public static void traceBegin(long traceTag, String methodName) { + @SystemApi(client = MODULE_LIBRARIES) + public static void traceBegin(long traceTag, @NonNull String methodName) { if (isTagEnabled(traceTag)) { nativeTraceBegin(traceTag, methodName); } @@ -217,6 +224,7 @@ public final class Trace { * @hide */ @UnsupportedAppUsage + @SystemApi(client = MODULE_LIBRARIES) public static void traceEnd(long traceTag) { if (isTagEnabled(traceTag)) { nativeTraceEnd(traceTag); @@ -237,7 +245,8 @@ public final class Trace { * @hide */ @UnsupportedAppUsage - public static void asyncTraceBegin(long traceTag, String methodName, int cookie) { + @SystemApi(client = MODULE_LIBRARIES) + public static void asyncTraceBegin(long traceTag, @NonNull String methodName, int cookie) { if (isTagEnabled(traceTag)) { nativeAsyncTraceBegin(traceTag, methodName, cookie); } @@ -255,7 +264,8 @@ public final class Trace { * @hide */ @UnsupportedAppUsage - public static void asyncTraceEnd(long traceTag, String methodName, int cookie) { + @SystemApi(client = MODULE_LIBRARIES) + public static void asyncTraceEnd(long traceTag, @NonNull String methodName, int cookie) { if (isTagEnabled(traceTag)) { nativeAsyncTraceEnd(traceTag, methodName, cookie); } diff --git a/core/java/android/service/security/attestationverification/OWNERS b/core/java/android/service/security/attestationverification/OWNERS new file mode 100644 index 000000000000..12c997868f3c --- /dev/null +++ b/core/java/android/service/security/attestationverification/OWNERS @@ -0,0 +1 @@ +include platform/frameworks/base:/core/java/android/security/attestationverification/OWNERS diff --git a/core/java/android/service/wallpapereffectsgeneration/OWNERS b/core/java/android/service/wallpapereffectsgeneration/OWNERS new file mode 100644 index 000000000000..d2d3e2c0a7b6 --- /dev/null +++ b/core/java/android/service/wallpapereffectsgeneration/OWNERS @@ -0,0 +1,4 @@ +susharon@google.com +shanh@google.com +huiwu@google.com +srazdan@google.com diff --git a/core/java/com/android/internal/midi/OWNERS b/core/java/com/android/internal/midi/OWNERS new file mode 100644 index 000000000000..af273a6f50e0 --- /dev/null +++ b/core/java/com/android/internal/midi/OWNERS @@ -0,0 +1 @@ +include /services/midi/OWNERS diff --git a/core/java/com/android/internal/os/BatteryStatsHistory.java b/core/java/com/android/internal/os/BatteryStatsHistory.java index 879e0a8cfe10..8ebb11dd752b 100644 --- a/core/java/com/android/internal/os/BatteryStatsHistory.java +++ b/core/java/com/android/internal/os/BatteryStatsHistory.java @@ -160,6 +160,11 @@ public class BatteryStatsHistory { mHistoryDir = null; mHistoryBuffer = historyBuffer; } + + public File getHistoryDirectory() { + return mHistoryDir; + } + /** * Set the active file that mHistoryBuffer is backed up into. * @@ -375,12 +380,24 @@ public class BatteryStatsHistory { } /** + * Read all history files and serialize into a big Parcel. + * Checkin file calls this method. + * @param out the output parcel + */ + public void writeToParcel(Parcel out) { + writeToParcel(out, false /* useBlobs */); + } + + /** * Read all history files and serialize into a big Parcel. This is to send history files to * Settings app since Settings app can not access /data/system directory. - * Checkin file also call this method. * @param out the output parcel */ - public void writeToParcel(Parcel out) { + public void writeToBatteryUsageStatsParcel(Parcel out) { + writeToParcel(out, true /* useBlobs */); + } + + private void writeToParcel(Parcel out, boolean useBlobs) { final long start = SystemClock.uptimeMillis(); out.writeInt(mFileNumbers.size() - 1); for(int i = 0; i < mFileNumbers.size() - 1; i++) { @@ -391,7 +408,12 @@ public class BatteryStatsHistory { } catch(Exception e) { Slog.e(TAG, "Error reading file "+ file.getBaseFile().getPath(), e); } - out.writeByteArray(raw); + if (useBlobs) { + out.writeBlob(raw); + } else { + // Avoiding blobs in the check-in file for compatibility + out.writeByteArray(raw); + } } if (DEBUG) { Slog.d(TAG, "writeToParcel duration ms:" + (SystemClock.uptimeMillis() - start)); @@ -399,18 +421,29 @@ public class BatteryStatsHistory { } /** - * This is for Settings app, when Settings app receives big history parcel, it call - * this method to parse it into list of parcels. - * Checkin file also call this method. + * This is for the check-in file, which has all history files embedded. * @param in the input parcel. */ public void readFromParcel(Parcel in) { + readFromParcel(in, false /* useBlobs */); + } + + /** + * This is for Settings app, when Settings app receives big history parcel, it calls + * this method to parse it into list of parcels. + * @param in the input parcel. + */ + public void readFromBatteryUsageStatsParcel(Parcel in) { + readFromParcel(in, true /* useBlobs */); + } + + private void readFromParcel(Parcel in, boolean useBlobs) { final long start = SystemClock.uptimeMillis(); mHistoryParcels = new ArrayList<>(); final int count = in.readInt(); for(int i = 0; i < count; i++) { - byte[] temp = in.createByteArray(); - if (temp.length == 0) { + byte[] temp = useBlobs ? in.readBlob() : in.createByteArray(); + if (temp == null || temp.length == 0) { continue; } Parcel p = Parcel.obtain(); diff --git a/core/java/com/android/internal/os/BatteryStatsImpl.java b/core/java/com/android/internal/os/BatteryStatsImpl.java index 270b5d6903b5..58a0622ba53b 100644 --- a/core/java/com/android/internal/os/BatteryStatsImpl.java +++ b/core/java/com/android/internal/os/BatteryStatsImpl.java @@ -83,7 +83,6 @@ import android.util.Log; import android.util.LongSparseArray; import android.util.LongSparseLongArray; import android.util.MutableInt; -import android.util.Pools; import android.util.PrintWriterPrinter; import android.util.Printer; import android.util.Slog; @@ -136,9 +135,7 @@ import java.util.Iterator; import java.util.LinkedList; import java.util.List; import java.util.Map; -import java.util.Objects; import java.util.Queue; -import java.util.Set; import java.util.concurrent.Future; import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.locks.ReentrantLock; @@ -1203,12 +1200,21 @@ public class BatteryStatsImpl extends BatteryStats { } public BatteryStatsImpl(Clocks clocks) { + this(clocks, (File) null); + } + + public BatteryStatsImpl(Clocks clocks, File historyDirectory) { init(clocks); mStartClockTimeMs = clocks.currentTimeMillis(); - mStatsFile = null; mCheckinFile = null; mDailyFile = null; - mBatteryStatsHistory = new BatteryStatsHistory(mHistoryBuffer); + if (historyDirectory == null) { + mStatsFile = null; + mBatteryStatsHistory = new BatteryStatsHistory(mHistoryBuffer); + } else { + mStatsFile = new AtomicFile(new File(historyDirectory, "batterystats.bin")); + mBatteryStatsHistory = new BatteryStatsHistory(this, historyDirectory, mHistoryBuffer); + } mHandler = null; mPlatformIdleStateCallback = null; mMeasuredEnergyRetriever = null; @@ -11522,8 +11528,6 @@ public class BatteryStatsImpl extends BatteryStats { } } - private final Pools.Pool<NetworkStats> mNetworkStatsPool = new Pools.SynchronizedPool<>(6); - private final Object mWifiNetworkLock = new Object(); @GuardedBy("mWifiNetworkLock") @@ -11541,13 +11545,15 @@ public class BatteryStatsImpl extends BatteryStats { private NetworkStats mLastModemNetworkStats = new NetworkStats(0, -1); @VisibleForTesting - protected NetworkStats readNetworkStatsLocked(@NonNull NetworkStatsManager networkStatsManager, - String[] ifaces) { - Objects.requireNonNull(networkStatsManager); - if (!ArrayUtils.isEmpty(ifaces)) { - return networkStatsManager.getDetailedUidStats(Set.of(ifaces)); - } - return null; + protected NetworkStats readMobileNetworkStatsLocked( + @NonNull NetworkStatsManager networkStatsManager) { + return networkStatsManager.getMobileUidStats(); + } + + @VisibleForTesting + protected NetworkStats readWifiNetworkStatsLocked( + @NonNull NetworkStatsManager networkStatsManager) { + return networkStatsManager.getWifiUidStats(); } /** @@ -11564,21 +11570,15 @@ public class BatteryStatsImpl extends BatteryStats { // Grab a separate lock to acquire the network stats, which may do I/O. NetworkStats delta = null; synchronized (mWifiNetworkLock) { - final NetworkStats latestStats = readNetworkStatsLocked(networkStatsManager, - mWifiIfaces); + final NetworkStats latestStats = readWifiNetworkStatsLocked(networkStatsManager); if (latestStats != null) { - delta = NetworkStats.subtract(latestStats, mLastWifiNetworkStats, null, null, - mNetworkStatsPool.acquire()); - mNetworkStatsPool.release(mLastWifiNetworkStats); + delta = latestStats.subtract(mLastWifiNetworkStats); mLastWifiNetworkStats = latestStats; } } synchronized (this) { if (!mOnBatteryInternal || mIgnoreNextExternalStats) { - if (delta != null) { - mNetworkStatsPool.release(delta); - } if (mIgnoreNextExternalStats) { // TODO: Strictly speaking, we should re-mark all 5 timers for each uid (and the // global one) here like we do for display. But I'm not sure it's worth the @@ -11599,61 +11599,60 @@ public class BatteryStatsImpl extends BatteryStats { long totalTxPackets = 0; long totalRxPackets = 0; if (delta != null) { - NetworkStats.Entry entry = new NetworkStats.Entry(); - final int size = delta.size(); - for (int i = 0; i < size; i++) { - entry = delta.getValues(i, entry); - + for (NetworkStats.Entry entry : delta) { if (DEBUG_ENERGY) { - Slog.d(TAG, "Wifi uid " + entry.uid + ": delta rx=" + entry.rxBytes - + " tx=" + entry.txBytes + " rxPackets=" + entry.rxPackets - + " txPackets=" + entry.txPackets); + Slog.d(TAG, "Wifi uid " + entry.getUid() + + ": delta rx=" + entry.getRxBytes() + + " tx=" + entry.getTxBytes() + + " rxPackets=" + entry.getRxPackets() + + " txPackets=" + entry.getTxPackets()); } - if (entry.rxBytes == 0 && entry.txBytes == 0) { + if (entry.getRxBytes() == 0 && entry.getTxBytes() == 0) { // Skip the lookup below since there is no work to do. continue; } - final Uid u = getUidStatsLocked(mapUid(entry.uid), elapsedRealtimeMs, uptimeMs); - if (entry.rxBytes != 0) { - u.noteNetworkActivityLocked(NETWORK_WIFI_RX_DATA, entry.rxBytes, - entry.rxPackets); - if (entry.set == NetworkStats.SET_DEFAULT) { // Background transfers - u.noteNetworkActivityLocked(NETWORK_WIFI_BG_RX_DATA, entry.rxBytes, - entry.rxPackets); + final Uid u = getUidStatsLocked(mapUid(entry.getUid()), + elapsedRealtimeMs, uptimeMs); + if (entry.getRxBytes() != 0) { + u.noteNetworkActivityLocked(NETWORK_WIFI_RX_DATA, entry.getRxBytes(), + entry.getRxPackets()); + if (entry.getSet() == NetworkStats.SET_DEFAULT) { // Background transfers + u.noteNetworkActivityLocked(NETWORK_WIFI_BG_RX_DATA, entry.getRxBytes(), + entry.getRxPackets()); } mNetworkByteActivityCounters[NETWORK_WIFI_RX_DATA].addCountLocked( - entry.rxBytes); + entry.getRxBytes()); mNetworkPacketActivityCounters[NETWORK_WIFI_RX_DATA].addCountLocked( - entry.rxPackets); + entry.getRxPackets()); // TODO(b/182845426): What if u was a mapped isolated uid? Shouldn't we sum? - rxPackets.put(u.getUid(), entry.rxPackets); + rxPackets.put(u.getUid(), entry.getRxPackets()); // Sum the total number of packets so that the Rx Power can // be evenly distributed amongst the apps. - totalRxPackets += entry.rxPackets; + totalRxPackets += entry.getRxPackets(); } - if (entry.txBytes != 0) { - u.noteNetworkActivityLocked(NETWORK_WIFI_TX_DATA, entry.txBytes, - entry.txPackets); - if (entry.set == NetworkStats.SET_DEFAULT) { // Background transfers - u.noteNetworkActivityLocked(NETWORK_WIFI_BG_TX_DATA, entry.txBytes, - entry.txPackets); + if (entry.getTxBytes() != 0) { + u.noteNetworkActivityLocked(NETWORK_WIFI_TX_DATA, entry.getTxBytes(), + entry.getTxPackets()); + if (entry.getSet() == NetworkStats.SET_DEFAULT) { // Background transfers + u.noteNetworkActivityLocked(NETWORK_WIFI_BG_TX_DATA, entry.getTxBytes(), + entry.getTxPackets()); } mNetworkByteActivityCounters[NETWORK_WIFI_TX_DATA].addCountLocked( - entry.txBytes); + entry.getTxBytes()); mNetworkPacketActivityCounters[NETWORK_WIFI_TX_DATA].addCountLocked( - entry.txPackets); + entry.getTxPackets()); // TODO(b/182845426): What if u was a mapped isolated uid? Shouldn't we sum? - txPackets.put(u.getUid(), entry.txPackets); + txPackets.put(u.getUid(), entry.getTxPackets()); // Sum the total number of packets so that the Tx Power can // be evenly distributed amongst the apps. - totalTxPackets += entry.txPackets; + totalTxPackets += entry.getTxPackets(); } // Calculate consumed energy for this uid. Only do so if WifiReporting isn't @@ -11681,11 +11680,10 @@ public class BatteryStatsImpl extends BatteryStats { uidEstimatedConsumptionMah.add(u.getUid(), mWifiPowerCalculator.calcPowerWithoutControllerDataMah( - entry.rxPackets, entry.txPackets, + entry.getRxPackets(), entry.getTxPackets(), uidRunningMs, uidScanMs, uidBatchScanMs)); } } - mNetworkStatsPool.release(delta); delta = null; } @@ -11932,21 +11930,15 @@ public class BatteryStatsImpl extends BatteryStats { // Grab a separate lock to acquire the network stats, which may do I/O. NetworkStats delta = null; synchronized (mModemNetworkLock) { - final NetworkStats latestStats = readNetworkStatsLocked(networkStatsManager, - mModemIfaces); + final NetworkStats latestStats = readMobileNetworkStatsLocked(networkStatsManager); if (latestStats != null) { - delta = NetworkStats.subtract(latestStats, mLastModemNetworkStats, null, null, - mNetworkStatsPool.acquire()); - mNetworkStatsPool.release(mLastModemNetworkStats); + delta = latestStats.subtract(mLastModemNetworkStats); mLastModemNetworkStats = latestStats; } } synchronized (this) { if (!mOnBatteryInternal || mIgnoreNextExternalStats) { - if (delta != null) { - mNetworkStatsPool.release(delta); - } return; } @@ -12148,7 +12140,6 @@ public class BatteryStatsImpl extends BatteryStats { totalEstimatedConsumptionMah); } - mNetworkStatsPool.release(delta); delta = null; } } diff --git a/core/java/com/android/internal/os/BatteryUsageStatsProvider.java b/core/java/com/android/internal/os/BatteryUsageStatsProvider.java index 980aec196079..79832867d01f 100644 --- a/core/java/com/android/internal/os/BatteryUsageStatsProvider.java +++ b/core/java/com/android/internal/os/BatteryUsageStatsProvider.java @@ -21,6 +21,7 @@ import android.hardware.SensorManager; import android.os.BatteryStats; import android.os.BatteryUsageStats; import android.os.BatteryUsageStatsQuery; +import android.os.Parcel; import android.os.SystemClock; import android.os.UidBatteryConsumer; import android.util.Log; @@ -28,6 +29,7 @@ import android.util.SparseArray; import com.android.internal.annotations.VisibleForTesting; +import java.io.File; import java.util.ArrayList; import java.util.Arrays; import java.util.List; @@ -186,16 +188,28 @@ public class BatteryUsageStatsProvider { } BatteryStatsImpl batteryStatsImpl = (BatteryStatsImpl) mStats; + + // Make a copy of battery history to avoid concurrent modification. + Parcel historyBuffer = Parcel.obtain(); + historyBuffer.appendFrom(batteryStatsImpl.mHistoryBuffer, 0, + batteryStatsImpl.mHistoryBuffer.dataSize()); + ArrayList<BatteryStats.HistoryTag> tags = new ArrayList<>( batteryStatsImpl.mHistoryTagPool.size()); for (Map.Entry<BatteryStats.HistoryTag, Integer> entry : batteryStatsImpl.mHistoryTagPool.entrySet()) { - final BatteryStats.HistoryTag tag = entry.getKey(); + final BatteryStats.HistoryTag tag = new BatteryStats.HistoryTag(); + tag.setTo(entry.getKey()); tag.poolIdx = entry.getValue(); tags.add(tag); } - batteryUsageStatsBuilder.setBatteryHistory(batteryStatsImpl.mHistoryBuffer, tags); + final File systemDir = + batteryStatsImpl.mBatteryStatsHistory.getHistoryDirectory().getParentFile(); + final BatteryStatsHistory batteryStatsHistory = + new BatteryStatsHistory(batteryStatsImpl, systemDir, historyBuffer); + + batteryUsageStatsBuilder.setBatteryHistory(historyBuffer, tags, batteryStatsHistory); } return batteryUsageStatsBuilder.build(); diff --git a/core/java/com/android/internal/os/BinderLatencyObserver.java b/core/java/com/android/internal/os/BinderLatencyObserver.java index 20cf102953e4..e9d55db3a5b4 100644 --- a/core/java/com/android/internal/os/BinderLatencyObserver.java +++ b/core/java/com/android/internal/os/BinderLatencyObserver.java @@ -19,7 +19,6 @@ package com.android.internal.os; import android.annotation.Nullable; import android.os.Binder; import android.os.Handler; -import android.os.Looper; import android.os.SystemClock; import android.util.ArrayMap; import android.util.Slog; @@ -181,7 +180,7 @@ public class BinderLatencyObserver { } public Handler getHandler() { - return new Handler(Looper.getMainLooper()); + return BackgroundThread.getHandler(); } } diff --git a/core/java/com/android/internal/os/RuntimeInit.java b/core/java/com/android/internal/os/RuntimeInit.java index 8d1f16b4b259..44c7f5406713 100644 --- a/core/java/com/android/internal/os/RuntimeInit.java +++ b/core/java/com/android/internal/os/RuntimeInit.java @@ -22,6 +22,7 @@ import android.app.ApplicationErrorReport; import android.app.IActivityManager; import android.compat.annotation.UnsupportedAppUsage; import android.content.type.DefaultMimeMapFactory; +import android.net.TrafficStats; import android.os.Build; import android.os.DeadObjectException; import android.os.IBinder; @@ -32,7 +33,6 @@ import android.util.Log; import android.util.Slog; import com.android.internal.logging.AndroidConfig; -import com.android.server.NetworkManagementSocketTagger; import dalvik.system.RuntimeHooks; import dalvik.system.VMRuntime; @@ -254,7 +254,7 @@ public class RuntimeInit { /* * Wire socket tagging to traffic stats. */ - NetworkManagementSocketTagger.install(); + TrafficStats.attachSocketTagger(); initialized = true; } diff --git a/core/jni/Android.bp b/core/jni/Android.bp index 07b16ed42624..adcbb425d1cf 100644 --- a/core/jni/Android.bp +++ b/core/jni/Android.bp @@ -245,7 +245,6 @@ cc_library_shared { "libandroid_net", "libandroidicu", "libbpf_android", - "libnetdbpf", "libnetdutils", "libmemtrack", "libandroidfw", diff --git a/core/jni/OWNERS b/core/jni/OWNERS index 832c49801bdc..80e83ad9865c 100644 --- a/core/jni/OWNERS +++ b/core/jni/OWNERS @@ -72,6 +72,9 @@ per-file AndroidRuntime.cpp = file:/graphics/java/android/graphics/OWNERS per-file AndroidRuntime.cpp = calin@google.com, ngeoffray@google.com, oth@google.com # Although marked "view" this is mostly graphics stuff per-file android_view_* = file:/graphics/java/android/graphics/OWNERS +# File used for Android Studio layoutlib +per-file LayoutlibLoader.cpp = file:/graphics/java/android/graphics/OWNERS +per-file LayoutlibLoader.cpp = diegoperez@google.com, jgaillard@google.com # Verity per-file com_android_internal_security_Verity* = ebiggers@google.com, victorhsieh@google.com diff --git a/core/jni/android_hardware_UsbDeviceConnection.cpp b/core/jni/android_hardware_UsbDeviceConnection.cpp index 845d65c67719..a0228428e90e 100644 --- a/core/jni/android_hardware_UsbDeviceConnection.cpp +++ b/core/jni/android_hardware_UsbDeviceConnection.cpp @@ -16,20 +16,19 @@ #define LOG_TAG "UsbDeviceConnectionJNI" -#include "utils/Log.h" - -#include "jni.h" +#include <fcntl.h> #include <nativehelper/JNIPlatformHelp.h> -#include "core_jni_helpers.h" - +#include <stdio.h> +#include <sys/stat.h> +#include <sys/types.h> #include <usbhost/usbhost.h> +#include <usbhost/usbhost_jni.h> #include <chrono> -#include <stdio.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <fcntl.h> +#include "core_jni_helpers.h" +#include "jni.h" +#include "utils/Log.h" using namespace android; using namespace std::chrono; @@ -91,22 +90,8 @@ android_hardware_UsbDeviceConnection_get_fd(JNIEnv *env, jobject thiz) static jbyteArray android_hardware_UsbDeviceConnection_get_desc(JNIEnv *env, jobject thiz) { - char buffer[16384]; int fd = android_hardware_UsbDeviceConnection_get_fd(env, thiz); - if (fd < 0) return NULL; - lseek(fd, 0, SEEK_SET); - int length = read(fd, buffer, sizeof(buffer)); - if (length < 0) return NULL; - - jbyteArray ret = env->NewByteArray(length); - if (ret) { - jbyte* bytes = (jbyte*)env->GetPrimitiveArrayCritical(ret, 0); - if (bytes) { - memcpy(bytes, buffer, length); - env->ReleasePrimitiveArrayCritical(ret, bytes, 0); - } - } - return ret; + return usb_jni_read_descriptors(env, fd); } static jboolean diff --git a/core/proto/OWNERS b/core/proto/OWNERS index 931ef4478098..43d2439b7f56 100644 --- a/core/proto/OWNERS +++ b/core/proto/OWNERS @@ -17,7 +17,8 @@ per-file usagestatsservice.proto, usagestatsservice_v2.proto = file:/core/java/a per-file apphibernationservice.proto = file:/core/java/android/apphibernation/OWNERS # Biometrics -kchyn@google.com +jaggies@google.com +jbolinger@google.com # Launcher hyunyoungs@google.com diff --git a/core/proto/android/os/incident.proto b/core/proto/android/os/incident.proto index 998ec96f6f23..51e150e28437 100644 --- a/core/proto/android/os/incident.proto +++ b/core/proto/android/os/incident.proto @@ -249,7 +249,8 @@ message IncidentProto { optional android.service.NetworkStatsServiceDumpProto netstats = 3001 [ (section).type = SECTION_DUMPSYS, - (section).args = "netstats --proto" + (section).args = "netstats --proto", + (section).userdebug_and_eng_only = true ]; optional android.providers.settings.SettingsServiceDumpProto settings = 3002 [ diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml index 2f334989b53a..ba647d7daa28 100644 --- a/core/res/res/values/config.xml +++ b/core/res/res/values/config.xml @@ -134,9 +134,6 @@ be sent during a change to the audio output device. --> <bool name="config_sendAudioBecomingNoisy">true</bool> - <!-- Whether Hearing Aid profile is supported --> - <bool name="config_hearing_aid_profile_supported">false</bool> - <!-- Flag to disable all transition animations --> <bool name="config_disableTransitionAnimation">false</bool> @@ -404,10 +401,6 @@ <string-array translatable="false" name="config_tether_bluetooth_regexs"> </string-array> - <!-- Max number of Bluetooth tethering connections allowed. If this is - updated config_tether_dhcp_range has to be updated appropriately. --> - <integer translatable="false" name="config_max_pan_devices">5</integer> - <!-- This setting is deprecated, please use com.android.networkstack.tethering.R.array.config_dhcp_range instead. --> <string-array translatable="false" name="config_tether_dhcp_range"> @@ -1820,53 +1813,38 @@ <!-- Integer to set a max latency the accelerometer will batch sensor requests with. --> <integer name="config_flipToScreenOffMaxLatencyMicros">2000000</integer> - <!-- Boolean indicating if current platform supports bluetooth SCO for off call - use cases --> + <!-- Note: This config is deprecated + Boolean indicating if current platform supports bluetooth SCO for off call + use cases + --> <bool name="config_bluetooth_sco_off_call">true</bool> - <!-- Boolean indicating if current platform supports bluetooth wide band - speech --> - <bool name="config_bluetooth_wide_band_speech">true</bool> - - <!-- Boolean indicating if current platform need do one-time bluetooth address - re-validation --> + <!-- Note: This config is deprecated + Boolean indicating if current platform need do one-time bluetooth address + re-validation + --> <bool name="config_bluetooth_address_validation">false</bool> - <!-- Boolean indicating if current platform supports BLE peripheral mode --> - <bool name="config_bluetooth_le_peripheral_mode_supported">false</bool> - - <!-- Boolean indicating if current platform supports HFP inband ringing --> - <bool name="config_bluetooth_hfp_inband_ringing_support">false</bool> - - <!-- Max number of scan filters supported by blutooth controller. 0 if the - device does not support hardware scan filters--> - <integer translatable="false" name="config_bluetooth_max_scan_filters">0</integer> - - <!-- Max number of advertisers supported by bluetooth controller. 0 if the - device does not support multiple advertisement--> - <integer translatable="false" name="config_bluetooth_max_advertisers">0</integer> - - <!-- Idle current for bluetooth controller. 0 by default--> + <!-- Note: This config is deprecated, use BluetoothProperties instead. + Idle current for bluetooth controller. 0 by default + --> <integer translatable="false" name="config_bluetooth_idle_cur_ma">0</integer> - <!-- Rx current for bluetooth controller. 0 by default--> + <!-- Note: This config is deprecated, use BluetoothProperties instead. + Rx current for bluetooth controller. 0 by default + --> <integer translatable="false" name="config_bluetooth_rx_cur_ma">0</integer> - <!-- Tx current for bluetooth controller. 0 by default--> + <!-- Note: This config is deprecated, use BluetoothProperties instead. + Tx current for bluetooth controller. 0 by default + --> <integer translatable="false" name="config_bluetooth_tx_cur_ma">0</integer> - <!-- Operating volatage for bluetooth controller. 0 by default--> + <!-- Note: This config is deprecated, use BluetoothProperties instead. + Operating volatage for bluetooth controller. 0 by default + --> <integer translatable="false" name="config_bluetooth_operating_voltage_mv">0</integer> - <!-- Max number of connected audio devices supported by Bluetooth stack --> - <integer name="config_bluetooth_max_connected_audio_devices">5</integer> - - <!-- Whether supported profiles should be reloaded upon enabling bluetooth --> - <bool name="config_bluetooth_reload_supported_profiles_when_enabled">false</bool> - - <!-- Enabling autoconnect over pan --> - <bool name="config_bluetooth_pan_enable_autoconnect">false</bool> - <!-- The default data-use polling period. --> <integer name="config_datause_polling_period_sec">600</integer> @@ -2007,10 +1985,6 @@ <!-- The name of the package that will be allowed to change its components' label/icon. --> <string name="config_overrideComponentUiPackage" translatable="false">com.android.stk</string> - <!-- Enable/disable default bluetooth profiles: - HSP_AG, ObexObjectPush, Audio, NAP --> - <bool name="config_bluetooth_default_profiles">true</bool> - <!-- IP address of the dns server to use if nobody else suggests one --> <string name="config_default_dns_server" translatable="false">8.8.8.8</string> @@ -4141,8 +4115,6 @@ <!-- Component name that should be granted Notification Assistant access --> <string name="config_defaultAssistantAccessComponent" translatable="false">android.ext.services/android.ext.services.notification.Assistant</string> - <bool name="config_supportBluetoothPersistedState">true</bool> - <bool name="config_keepRestrictedProfilesInBackground">true</bool> <!-- Cellular network service package name to bind to by default. --> diff --git a/core/res/res/values/public.xml b/core/res/res/values/public.xml index 2403a605972e..6ef5bd46dce7 100644 --- a/core/res/res/values/public.xml +++ b/core/res/res/values/public.xml @@ -3200,11 +3200,87 @@ <!-- @hide For use by platform and tools only. Developers should not specify this value. --> <public type="string" name="config_defaultRingtoneVibrationSound" id="0x0104003b" /> + <!-- =============================================================== + Resources added in version T of the platform + + NOTE: add <public> elements within a <staging-public-group> like so: + + <staging-public-group type="attr" first-id="0x01ff0000"> + <public name="exampleAttr1" /> + <public name="exampleAttr2" /> + </staging-public-group> + + To add a new <staging-public-group> block, find the id value for the + last <staging-public-group> block defined for thie API level, and + subtract 0x00010000 from it to get to the id of the new block. + + For example, if the block closest to the end of this file has an id + of 0x01ee0000, the id of the new block should be 0x01ed0000 + (0x01ee0000 - 0x00010000 = 0x01ed0000). + =============================================================== --> + <eat-comment /> + + <staging-public-group type="attr" first-id="0x01df0000"> + </staging-public-group> + + <staging-public-group type="id" first-id="0x01de0000"> + </staging-public-group> + + <staging-public-group type="style" first-id="0x0dfd0000"> + </staging-public-group> + + <staging-public-group type="string" first-id="0x0dfc0000"> + </staging-public-group> + + <staging-public-group type="dimen" first-id="0x01db0000"> + </staging-public-group> + + <staging-public-group type="color" first-id="0x01da0000"> + </staging-public-group> + + <staging-public-group type="array" first-id="0x01d90000"> + <!-- @hide @SystemApi --> + <public name="config_optionalIpSecAlgorithms" /> + </staging-public-group> + + <staging-public-group type="drawable" first-id="0x01d80000"> + </staging-public-group> + + <staging-public-group type="layout" first-id="0x01d70000"> + </staging-public-group> + + <staging-public-group type="anim" first-id="0x01d60000"> + </staging-public-group> + + <staging-public-group type="animator" first-id="0x01d50000"> + </staging-public-group> + + <staging-public-group type="interpolator" first-id="0x01d40000"> + </staging-public-group> + + <staging-public-group type="mipmap" first-id="0x01d30000"> + </staging-public-group> + + <staging-public-group type="integer" first-id="0x01d20000"> + </staging-public-group> + + <staging-public-group type="transition" first-id="0x01d10000"> + </staging-public-group> + + <staging-public-group type="raw" first-id="0x01d00000"> + </staging-public-group> + + <staging-public-group type="bool" first-id="0x01cf0000"> + </staging-public-group> + + <staging-public-group type="fraction" first-id="0x01ce0000"> + </staging-public-group> + <!-- =============================================================== DO NOT ADD UN-GROUPED ITEMS HERE Any new items (attrs, styles, ids, etc.) *must* be added in a - public-group block, as the preceding comment explains. + staging-public-group block, as the preceding comment explains. Items added outside of a group may have their value recalculated every time something new is added to this file. =============================================================== --> diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml index 4db6499569b3..590fcf46f373 100644 --- a/core/res/res/values/symbols.xml +++ b/core/res/res/values/symbols.xml @@ -278,8 +278,6 @@ <java-symbol type="bool" name="config_flipToScreenOffEnabled" /> <java-symbol type="integer" name="config_flipToScreenOffMaxLatencyMicros" /> <java-symbol type="bool" name="config_bluetooth_sco_off_call" /> - <java-symbol type="bool" name="config_bluetooth_le_peripheral_mode_supported" /> - <java-symbol type="bool" name="config_bluetooth_hfp_inband_ringing_support" /> <java-symbol type="bool" name="config_cellBroadcastAppLinks" /> <java-symbol type="bool" name="config_duplicate_port_omadm_wappush" /> <java-symbol type="bool" name="config_disableTransitionAnimation" /> @@ -343,7 +341,6 @@ <java-symbol type="integer" name="config_timeZoneRulesCheckRetryCount" /> <java-symbol type="bool" name="config_sendAudioBecomingNoisy" /> <java-symbol type="bool" name="config_enableScreenshotChord" /> - <java-symbol type="bool" name="config_bluetooth_default_profiles" /> <java-symbol type="bool" name="config_enableWifiDisplay" /> <java-symbol type="bool" name="config_allowAnimationsInLowPowerMode" /> <java-symbol type="bool" name="config_useDevInputEventForAudioJack" /> @@ -417,9 +414,6 @@ <java-symbol type="dimen" name="config_pictureInPictureMaxAspectRatio" /> <java-symbol type="integer" name="config_pictureInPictureMaxNumberOfActions" /> <java-symbol type="dimen" name="config_closeToSquareDisplayMaxAspectRatio" /> - <java-symbol type="integer" name="config_bluetooth_max_advertisers" /> - <java-symbol type="integer" name="config_bluetooth_max_scan_filters" /> - <java-symbol type="integer" name="config_bluetooth_max_connected_audio_devices" /> <java-symbol type="integer" name="config_burnInProtectionMinHorizontalOffset" /> <java-symbol type="integer" name="config_burnInProtectionMaxHorizontalOffset" /> <java-symbol type="integer" name="config_burnInProtectionMinVerticalOffset" /> @@ -429,9 +423,6 @@ <java-symbol type="integer" name="config_bluetooth_rx_cur_ma" /> <java-symbol type="integer" name="config_bluetooth_tx_cur_ma" /> <java-symbol type="integer" name="config_bluetooth_operating_voltage_mv" /> - <java-symbol type="bool" name="config_bluetooth_pan_enable_autoconnect" /> - <java-symbol type="bool" name="config_bluetooth_reload_supported_profiles_when_enabled" /> - <java-symbol type="bool" name="config_hearing_aid_profile_supported" /> <java-symbol type="integer" name="config_cursorWindowSize" /> <java-symbol type="integer" name="config_drawLockTimeoutMillis" /> <java-symbol type="integer" name="config_doublePressOnPowerBehavior" /> @@ -450,7 +441,6 @@ <java-symbol type="integer" name="config_wakeUpToLastStateTimeoutMillis" /> <java-symbol type="integer" name="config_lowMemoryKillerMinFreeKbytesAdjust" /> <java-symbol type="integer" name="config_lowMemoryKillerMinFreeKbytesAbsolute" /> - <java-symbol type="integer" name="config_max_pan_devices" /> <java-symbol type="integer" name="config_ntpPollingInterval" /> <java-symbol type="integer" name="config_ntpPollingIntervalShorter" /> <java-symbol type="integer" name="config_ntpRetry" /> @@ -3782,8 +3772,6 @@ <java-symbol type="string" name="config_defaultAssistantAccessComponent" /> - <java-symbol type="bool" name="config_supportBluetoothPersistedState" /> - <java-symbol type="string" name="slices_permission_request" /> <java-symbol type="string" name="screenshot_edit" /> diff --git a/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsProviderTest.java b/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsProviderTest.java index 74b6dbe76a16..93910b9c816e 100644 --- a/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsProviderTest.java +++ b/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsProviderTest.java @@ -39,6 +39,8 @@ import androidx.test.InstrumentationRegistry; import androidx.test.filters.SmallTest; import androidx.test.runner.AndroidJUnit4; +import libcore.testing.io.TestIoUtils; + import org.junit.Rule; import org.junit.Test; import org.junit.runner.RunWith; @@ -52,8 +54,11 @@ public class BatteryUsageStatsProviderTest { private static final int APP_UID = Process.FIRST_APPLICATION_UID + 42; private static final long MINUTE_IN_MS = 60 * 1000; + private final File mHistoryDir = + TestIoUtils.createTemporaryDirectory(getClass().getSimpleName()); + @Rule - public final BatteryUsageStatsRule mStatsRule = new BatteryUsageStatsRule(12345) + public final BatteryUsageStatsRule mStatsRule = new BatteryUsageStatsRule(12345, mHistoryDir) .setAveragePower(PowerProfile.POWER_FLASHLIGHT, 360.0); @Test diff --git a/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsRule.java b/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsRule.java index 083090c54619..2c6f5fa1ae82 100644 --- a/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsRule.java +++ b/core/tests/coretests/src/com/android/internal/os/BatteryUsageStatsRule.java @@ -40,6 +40,7 @@ import org.junit.runner.Description; import org.junit.runners.model.Statement; import org.mockito.stubbing.Answer; +import java.io.File; import java.util.Arrays; public class BatteryUsageStatsRule implements TestRule { @@ -57,14 +58,18 @@ public class BatteryUsageStatsRule implements TestRule { private boolean mScreenOn; public BatteryUsageStatsRule() { - this(0); + this(0, null); } public BatteryUsageStatsRule(long currentTime) { + this(currentTime, null); + } + + public BatteryUsageStatsRule(long currentTime, File historyDir) { Context context = InstrumentationRegistry.getContext(); mPowerProfile = spy(new PowerProfile(context, true /* forTest */)); mMockClocks.currentTime = currentTime; - mBatteryStats = new MockBatteryStatsImpl(mMockClocks); + mBatteryStats = new MockBatteryStatsImpl(mMockClocks, historyDir); mBatteryStats.setPowerProfile(mPowerProfile); mBatteryStats.onSystemReady(); } diff --git a/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java b/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java index db0c934bd0d4..11d20f2ebeb0 100644 --- a/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java +++ b/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java @@ -29,6 +29,7 @@ import com.android.internal.os.KernelCpuUidTimeReader.KernelCpuUidFreqTimeReader import com.android.internal.os.KernelCpuUidTimeReader.KernelCpuUidUserSysTimeReader; import com.android.internal.power.MeasuredEnergyStats; +import java.io.File; import java.util.ArrayList; import java.util.Arrays; import java.util.Queue; @@ -40,10 +41,16 @@ import java.util.concurrent.Future; public class MockBatteryStatsImpl extends BatteryStatsImpl { public BatteryStatsImpl.Clocks clocks; public boolean mForceOnBattery; + // The mNetworkStats will be used for both wifi and mobile categories private NetworkStats mNetworkStats; MockBatteryStatsImpl(Clocks clocks) { - super(clocks); + this(clocks, null); + } + + MockBatteryStatsImpl(Clocks clocks, File historyDirectory) { + super(clocks, historyDirectory); + this.clocks = mClocks; initTimersAndCounters(); @@ -107,11 +114,16 @@ public class MockBatteryStatsImpl extends BatteryStatsImpl { } @Override - protected NetworkStats readNetworkStatsLocked(@NonNull NetworkStatsManager networkStatsManager, - String[] ifaces) { + protected NetworkStats readMobileNetworkStatsLocked( + @NonNull NetworkStatsManager networkStatsManager) { return mNetworkStats; } + @Override + protected NetworkStats readWifiNetworkStatsLocked( + @NonNull NetworkStatsManager networkStatsManager) { + return mNetworkStats; + } public MockBatteryStatsImpl setPowerProfile(PowerProfile powerProfile) { mPowerProfile = powerProfile; return this; diff --git a/data/etc/privapp-permissions-platform.xml b/data/etc/privapp-permissions-platform.xml index fefcebeaef20..fa6b086b9259 100644 --- a/data/etc/privapp-permissions-platform.xml +++ b/data/etc/privapp-permissions-platform.xml @@ -390,6 +390,9 @@ applications that come with the platform <permission name="android.permission.SET_WALLPAPER" /> <permission name="android.permission.SET_WALLPAPER_COMPONENT" /> <permission name="android.permission.REQUEST_NOTIFICATION_ASSISTANT_SERVICE" /> + <!-- Permission required for CTS test - TrustTestCases --> + <permission name="android.permission.PROVIDE_TRUST_AGENT" /> + <permission name="android.permission.ACCESS_KEYGUARD_SECURE_STORAGE" /> <!-- Permissions required for Incremental CTS tests --> <permission name="com.android.permission.USE_INSTALLER_V2"/> <permission name="android.permission.LOADER_USAGE_STATS"/> @@ -458,6 +461,7 @@ applications that come with the platform <!-- Permission needed for CTS test - WifiManagerTest --> <permission name="android.permission.WIFI_ACCESS_COEX_UNSAFE_CHANNELS" /> <permission name="android.permission.WIFI_UPDATE_COEX_UNSAFE_CHANNELS" /> + <permission name="android.permission.OVERRIDE_WIFI_CONFIG" /> <!-- Permission required for CTS test CarrierMessagingServiceWrapperTest --> <permission name="android.permission.BIND_CARRIER_SERVICES"/> <!-- Permission required for CTS test - MusicRecognitionManagerTest --> diff --git a/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/apppairs/OWNERS b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/apppairs/OWNERS new file mode 100644 index 000000000000..8446b37dbf06 --- /dev/null +++ b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/apppairs/OWNERS @@ -0,0 +1,2 @@ +# window manager > wm shell > Split Screen +# Bug component: 928697 diff --git a/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/bubble/OWNERS b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/bubble/OWNERS new file mode 100644 index 000000000000..566acc87e42d --- /dev/null +++ b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/bubble/OWNERS @@ -0,0 +1,2 @@ +# window manager > wm shell > Bubbles +# Bug component: 555586 diff --git a/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/legacysplitscreen/OWNERS b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/legacysplitscreen/OWNERS new file mode 100644 index 000000000000..8446b37dbf06 --- /dev/null +++ b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/legacysplitscreen/OWNERS @@ -0,0 +1,2 @@ +# window manager > wm shell > Split Screen +# Bug component: 928697 diff --git a/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/pip/OWNERS b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/pip/OWNERS new file mode 100644 index 000000000000..172e24bf4574 --- /dev/null +++ b/libs/WindowManager/Shell/tests/flicker/src/com/android/wm/shell/flicker/pip/OWNERS @@ -0,0 +1,2 @@ +# window manager > wm shell > Picture-In-Picture +# Bug component: 316251 diff --git a/media/java/android/media/MediaCodecInfo.java b/media/java/android/media/MediaCodecInfo.java index 3c152fb68c0a..41c8887250ee 100644 --- a/media/java/android/media/MediaCodecInfo.java +++ b/media/java/android/media/MediaCodecInfo.java @@ -426,10 +426,30 @@ public final class MediaCodecInfo { /** @deprecated Use {@link #COLOR_Format32bitABGR8888}. */ public static final int COLOR_Format24BitABGR6666 = 43; - /** @hide - * P010 is a 4:2:0 YCbCr semiplanar format comprised of a WxH Y plane - * followed by a Wx(H/2) CbCr plane. Each sample is represented by a 16-bit - * little-endian value, with the lower 6 bits set to zero. */ + /** + * P010 is 10-bit-per component 4:2:0 YCbCr semiplanar format. + * <p> + * This format uses 24 allocated bits per pixel with 15 bits of + * data per pixel. Chroma planes are subsampled by 2 both + * horizontally and vertically. Each chroma and luma component + * has 16 allocated bits in little-endian configuration with 10 + * MSB of actual data. + * + * <pre> + * byte byte + * <--------- i --------> | <------ i + 1 ------> + * +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+ + * | UNUSED | Y/Cb/Cr | + * +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+ + * 0 5 6 7 0 7 + * bit + * </pre> + * + * Use this format with {@link Image}. This format corresponds + * to {@link android.graphics.ImageFormat#YCBCR_P010}. + * <p> + */ + @SuppressLint("AllUpper") public static final int COLOR_FormatYUVP010 = 54; /** @deprecated Use {@link #COLOR_FormatYUV420Flexible}. */ @@ -439,6 +459,25 @@ public final class MediaCodecInfo { public static final int COLOR_FormatSurface = 0x7F000789; /** + * 64 bits per pixel RGBA color format, with 16-bit signed + * floating point red, green, blue, and alpha components. + * <p> + * + * <pre> + * byte byte byte byte + * <-- i -->|<- i+1 ->|<- i+2 ->|<- i+3 ->|<- i+4 ->|<- i+5 ->|<- i+6 ->|<- i+7 -> + * +---------+---------+-------------------+---------+---------+---------+---------+ + * | RED | GREEN | BLUE | ALPHA | + * +---------+---------+-------------------+---------+---------+---------+---------+ + * 0 7 0 7 0 7 0 7 0 7 0 7 0 7 0 7 + * </pre> + * + * This corresponds to {@link android.graphics.PixelFormat#RGBA_F16}. + */ + @SuppressLint("AllUpper") + public static final int COLOR_Format64bitABGRFloat = 0x7F000F16; + + /** * 32 bits per pixel RGBA color format, with 8-bit red, green, blue, and alpha components. * <p> * Using 32-bit little-endian representation, colors stored as Red 7:0, Green 15:8, @@ -456,6 +495,26 @@ public final class MediaCodecInfo { public static final int COLOR_Format32bitABGR8888 = 0x7F00A000; /** + * 32 bits per pixel RGBA color format, with 10-bit red, green, + * blue, and 2-bit alpha components. + * <p> + * Using 32-bit little-endian representation, colors stored as + * Red 9:0, Green 19:10, Blue 29:20, and Alpha 31:30. + * <pre> + * byte byte byte byte + * <------ i -----> | <---- i+1 ----> | <---- i+2 ----> | <---- i+3 -----> + * +-----------------+---+-------------+-------+---------+-----------+-----+ + * | RED | GREEN | BLUE |ALPHA| + * +-----------------+---+-------------+-------+---------+-----------+-----+ + * 0 7 0 1 2 7 0 3 4 7 0 5 6 7 + * </pre> + * + * This corresponds to {@link android.graphics.PixelFormat#RGBA_1010102}. + */ + @SuppressLint("AllUpper") + public static final int COLOR_Format32bitABGR2101010 = 0x7F00AAA2; + + /** * Flexible 12 bits per pixel, subsampled YUV color format with 8-bit chroma and luma * components. * <p> @@ -603,6 +662,18 @@ public final class MediaCodecInfo { public static final String FEATURE_QpBounds = "qp-bounds"; /** + * <b>video encoder only</b>: codec supports exporting encoding statistics. + * Encoders with this feature can provide the App clients with the encoding statistics + * information about the frame. + * The scope of encoding statistics is controlled by + * {@link MediaFormat#KEY_VIDEO_ENCODING_STATISTICS_LEVEL}. + * + * @see MediaFormat#KEY_VIDEO_ENCODING_STATISTICS_LEVEL + */ + @SuppressLint("AllUpper") // for consistency with other FEATURE_* constants + public static final String FEATURE_EncodingStatistics = "encoding-statistics"; + + /** * Query codec feature capabilities. * <p> * These features are supported to be used by the codec. These @@ -641,6 +712,7 @@ public final class MediaCodecInfo { new Feature(FEATURE_MultipleFrames, (1 << 1), false), new Feature(FEATURE_DynamicTimestamp, (1 << 2), false), new Feature(FEATURE_QpBounds, (1 << 3), false), + new Feature(FEATURE_EncodingStatistics, (1 << 4), false), // feature to exclude codec from REGULAR codec list new Feature(FEATURE_SpecialCodec, (1 << 30), false, true), }; diff --git a/media/java/android/media/MediaFormat.java b/media/java/android/media/MediaFormat.java index 9bf0db52f66d..aa5c404800e8 100644 --- a/media/java/android/media/MediaFormat.java +++ b/media/java/android/media/MediaFormat.java @@ -1102,6 +1102,76 @@ public final class MediaFormat { public static final String KEY_VIDEO_QP_B_MIN = "video-qp-b-min"; /** + * A key describing the level of encoding statistics information emitted from video encoder. + * + * The associated value is an integer. + */ + public static final String KEY_VIDEO_ENCODING_STATISTICS_LEVEL = + "video-encoding-statistics-level"; + + /** + * Encoding Statistics Level None. + * Encoder generates no information about Encoding statistics. + */ + public static final int VIDEO_ENCODING_STATISTICS_LEVEL_NONE = 0; + + /** + * Encoding Statistics Level 1. + * Encoder generates {@link MediaFormat#KEY_PICTURE_TYPE} and + * {@link MediaFormat#KEY_VIDEO_QP_AVERAGE} for each frame. + */ + public static final int VIDEO_ENCODING_STATISTICS_LEVEL_1 = 1; + + /** @hide */ + @IntDef({ + VIDEO_ENCODING_STATISTICS_LEVEL_NONE, + VIDEO_ENCODING_STATISTICS_LEVEL_1, + }) + @Retention(RetentionPolicy.SOURCE) + public @interface VideoEncodingStatisticsLevel {} + + /** + * A key describing the per-frame average block QP (Quantization Parameter). + * This is a part of a video 'Encoding Statistics' export feature. + * This value is emitted from video encoder for a video frame. + * The average value is rounded down (using floor()) to integer value. + * + * The associated value is an integer. + */ + public static final String KEY_VIDEO_QP_AVERAGE = "video-qp-average"; + + /** + * A key describing the picture type of the encoded frame. + * This is a part of a video 'Encoding Statistics' export feature. + * This value is emitted from video encoder for a video frame. + * + * The associated value is an integer. + */ + public static final String KEY_PICTURE_TYPE = "picture-type"; + + /** Picture Type is unknown. */ + public static final int PICTURE_TYPE_UNKNOWN = 0; + + /** Picture Type is I Frame. */ + public static final int PICTURE_TYPE_I = 1; + + /** Picture Type is P Frame. */ + public static final int PICTURE_TYPE_P = 2; + + /** Picture Type is B Frame. */ + public static final int PICTURE_TYPE_B = 3; + + /** @hide */ + @IntDef({ + PICTURE_TYPE_UNKNOWN, + PICTURE_TYPE_I, + PICTURE_TYPE_P, + PICTURE_TYPE_B, + }) + @Retention(RetentionPolicy.SOURCE) + public @interface PictureType {} + + /** * A key describing the audio session ID of the AudioTrack associated * to a tunneled video codec. * The associated value is an integer. diff --git a/packages/ConnectivityT/framework-t/Android.bp b/packages/ConnectivityT/framework-t/Android.bp index d3d8bba16c7c..223bdcdd9c95 100644 --- a/packages/ConnectivityT/framework-t/Android.bp +++ b/packages/ConnectivityT/framework-t/Android.bp @@ -129,6 +129,11 @@ filegroup { "src/android/net/EthernetNetworkSpecifier.java", "src/android/net/IEthernetManager.aidl", "src/android/net/IEthernetServiceListener.aidl", + "src/android/net/IInternalNetworkManagementListener.aidl", + "src/android/net/InternalNetworkUpdateRequest.java", + "src/android/net/InternalNetworkUpdateRequest.aidl", + "src/android/net/InternalNetworkManagementException.java", + "src/android/net/InternalNetworkManagementException.aidl", "src/android/net/ITetheredInterfaceCallback.aidl", ], path: "src", diff --git a/packages/ConnectivityT/framework-t/src/android/app/usage/NetworkStatsManager.java b/packages/ConnectivityT/framework-t/src/android/app/usage/NetworkStatsManager.java index 4b906c908959..28f930ff1207 100644 --- a/packages/ConnectivityT/framework-t/src/android/app/usage/NetworkStatsManager.java +++ b/packages/ConnectivityT/framework-t/src/android/app/usage/NetworkStatsManager.java @@ -17,8 +17,11 @@ package android.app.usage; import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; +import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR; +import static android.net.NetworkCapabilities.TRANSPORT_WIFI; import android.Manifest; +import android.annotation.CallbackExecutor; import android.annotation.NonNull; import android.annotation.Nullable; import android.annotation.RequiresPermission; @@ -37,14 +40,11 @@ import android.net.NetworkStack; import android.net.NetworkStateSnapshot; import android.net.NetworkTemplate; import android.net.UnderlyingNetworkInfo; +import android.net.netstats.IUsageCallback; import android.net.netstats.provider.INetworkStatsProviderCallback; import android.net.netstats.provider.NetworkStatsProvider; -import android.os.Binder; import android.os.Build; import android.os.Handler; -import android.os.Looper; -import android.os.Message; -import android.os.Messenger; import android.os.RemoteException; import android.telephony.TelephonyManager; import android.text.TextUtils; @@ -55,7 +55,7 @@ import com.android.net.module.util.NetworkIdentityUtils; import java.util.List; import java.util.Objects; -import java.util.Set; +import java.util.concurrent.Executor; /** * Provides access to network usage history and statistics. Usage data is collected in @@ -125,6 +125,19 @@ public class NetworkStatsManager { private final Context mContext; private final INetworkStatsService mService; + /** + * Type constants for reading different types of Data Usage. + * @hide + */ + // @SystemApi(client = MODULE_LIBRARIES) + public static final String PREFIX_DEV = "dev"; + /** @hide */ + public static final String PREFIX_XT = "xt"; + /** @hide */ + public static final String PREFIX_UID = "uid"; + /** @hide */ + public static final String PREFIX_UID_TAG = "uid_tag"; + /** @hide */ public static final int FLAG_POLL_ON_OPEN = 1 << 0; /** @hide */ @@ -143,6 +156,11 @@ public class NetworkStatsManager { setAugmentWithSubscriptionPlan(true); } + /** @hide */ + public INetworkStatsService getBinder() { + return mService; + } + /** * Set poll on open flag to indicate the poll is needed before service gets statistics * result. This is default enabled. However, for any non-privileged caller, the poll might @@ -211,9 +229,10 @@ public class NetworkStatsManager { */ @NonNull @WorkerThread - // @SystemApi(client = MODULE_LIBRARIES) + @SystemApi(client = MODULE_LIBRARIES) public Bucket querySummaryForDevice(@NonNull NetworkTemplate template, long startTime, long endTime) { + Objects.requireNonNull(template); try { NetworkStats stats = new NetworkStats(mContext, template, mFlags, startTime, endTime, mService); @@ -385,10 +404,11 @@ public class NetworkStatsManager { * @hide */ @NonNull - // @SystemApi(client = MODULE_LIBRARIES) + @SystemApi(client = MODULE_LIBRARIES) @WorkerThread public NetworkStats querySummary(@NonNull NetworkTemplate template, long startTime, long endTime) throws SecurityException { + Objects.requireNonNull(template); try { NetworkStats result = new NetworkStats(mContext, template, mFlags, startTime, endTime, mService); @@ -418,10 +438,11 @@ public class NetworkStatsManager { * @hide */ @NonNull - // @SystemApi(client = MODULE_LIBRARIES) + @SystemApi(client = MODULE_LIBRARIES) @WorkerThread public NetworkStats queryTaggedSummary(@NonNull NetworkTemplate template, long startTime, long endTime) throws SecurityException { + Objects.requireNonNull(template); try { NetworkStats result = new NetworkStats(mContext, template, mFlags, startTime, endTime, mService); @@ -453,10 +474,11 @@ public class NetworkStatsManager { * @hide */ @NonNull - // @SystemApi(client = MODULE_LIBRARIES) + @SystemApi(client = MODULE_LIBRARIES) @WorkerThread public NetworkStats queryDetailsForDevice(@NonNull NetworkTemplate template, long startTime, long endTime) { + Objects.requireNonNull(template); try { final NetworkStats result = new NetworkStats(mContext, template, mFlags, startTime, endTime, mService); @@ -580,10 +602,11 @@ public class NetworkStatsManager { * @hide */ @NonNull - // @SystemApi(client = MODULE_LIBRARIES) + @SystemApi(client = MODULE_LIBRARIES) @WorkerThread public NetworkStats queryDetailsForUidTagState(@NonNull NetworkTemplate template, long startTime, long endTime, int uid, int tag, int state) throws SecurityException { + Objects.requireNonNull(template); try { final NetworkStats result = new NetworkStats( mContext, template, mFlags, startTime, endTime, mService); @@ -652,50 +675,83 @@ public class NetworkStatsManager { } /** - * Query realtime network usage statistics details with interfaces constrains. - * Return snapshot of current UID statistics, including any {@link TrafficStats#UID_TETHERING}, - * video calling data usage and count of network operations that set by - * {@link TrafficStats#incrementOperationCount}. The returned data doesn't include any - * statistics that is reported by {@link NetworkStatsProvider}. + * Query realtime mobile network usage statistics. * - * @param requiredIfaces A list of interfaces the stats should be restricted to, or - * {@link NetworkStats#INTERFACES_ALL}. + * Return a snapshot of current UID network statistics, as it applies + * to the mobile radios of the device. The snapshot will include any + * tethering traffic, video calling data usage and count of + * network operations set by {@link TrafficStats#incrementOperationCount} + * made over a mobile radio. + * The snapshot will not include any statistics that cannot be seen by + * the kernel, e.g. statistics reported by {@link NetworkStatsProvider}s. * * @hide */ - //@SystemApi + @SystemApi @RequiresPermission(NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) - @NonNull public android.net.NetworkStats getDetailedUidStats( - @NonNull Set<String> requiredIfaces) { - Objects.requireNonNull(requiredIfaces, "requiredIfaces cannot be null"); + @NonNull public android.net.NetworkStats getMobileUidStats() { try { - return mService.getDetailedUidStats(requiredIfaces.toArray(new String[0])); + return mService.getUidStatsForTransport(TRANSPORT_CELLULAR); } catch (RemoteException e) { - if (DBG) Log.d(TAG, "Remote exception when get detailed uid stats"); + if (DBG) Log.d(TAG, "Remote exception when get Mobile uid stats"); throw e.rethrowFromSystemServer(); } } - /** @hide */ - public void registerUsageCallback(NetworkTemplate template, int networkType, - long thresholdBytes, UsageCallback callback, @Nullable Handler handler) { - Objects.requireNonNull(callback, "UsageCallback cannot be null"); - - final Looper looper; - if (handler == null) { - looper = Looper.myLooper(); - } else { - looper = handler.getLooper(); + /** + * Query realtime Wi-Fi network usage statistics. + * + * Return a snapshot of current UID network statistics, as it applies + * to the Wi-Fi radios of the device. The snapshot will include any + * tethering traffic, video calling data usage and count of + * network operations set by {@link TrafficStats#incrementOperationCount} + * made over a Wi-Fi radio. + * The snapshot will not include any statistics that cannot be seen by + * the kernel, e.g. statistics reported by {@link NetworkStatsProvider}s. + * + * @hide + */ + @SystemApi + @RequiresPermission(NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK) + @NonNull public android.net.NetworkStats getWifiUidStats() { + try { + return mService.getUidStatsForTransport(TRANSPORT_WIFI); + } catch (RemoteException e) { + if (DBG) Log.d(TAG, "Remote exception when get WiFi uid stats"); + throw e.rethrowFromSystemServer(); } + } - DataUsageRequest request = new DataUsageRequest(DataUsageRequest.REQUEST_ID_UNSET, + /** + * Registers to receive notifications about data usage on specified networks. + * + * <p>The callbacks will continue to be called as long as the process is alive or + * {@link #unregisterUsageCallback} is called. + * + * @param template Template used to match networks. See {@link NetworkTemplate}. + * @param thresholdBytes Threshold in bytes to be notified on. The provided value that lower + * than 2MiB will be clamped for non-privileged callers. + * @param executor The executor on which callback will be invoked. The provided {@link Executor} + * must run callback sequentially, otherwise the order of callbacks cannot be + * guaranteed. + * @param callback The {@link UsageCallback} that the system will call when data usage + * has exceeded the specified threshold. + * @hide + */ + @SystemApi(client = MODULE_LIBRARIES) + public void registerUsageCallback(@NonNull NetworkTemplate template, long thresholdBytes, + @NonNull @CallbackExecutor Executor executor, @NonNull UsageCallback callback) { + Objects.requireNonNull(template, "NetworkTemplate cannot be null"); + Objects.requireNonNull(callback, "UsageCallback cannot be null"); + Objects.requireNonNull(executor, "Executor cannot be null"); + + final DataUsageRequest request = new DataUsageRequest(DataUsageRequest.REQUEST_ID_UNSET, template, thresholdBytes); try { - CallbackHandler callbackHandler = new CallbackHandler(looper, networkType, - template.getSubscriberId(), callback); + final UsageCallbackWrapper callbackWrapper = + new UsageCallbackWrapper(executor, callback); callback.request = mService.registerUsageCallback( - mContext.getOpPackageName(), request, new Messenger(callbackHandler), - new Binder()); + mContext.getOpPackageName(), request, callbackWrapper); if (DBG) Log.d(TAG, "registerUsageCallback returned " + callback.request); if (callback.request == null) { @@ -748,12 +804,15 @@ public class NetworkStatsManager { NetworkTemplate template = createTemplate(networkType, subscriberId); if (DBG) { Log.d(TAG, "registerUsageCallback called with: {" - + " networkType=" + networkType - + " subscriberId=" + subscriberId - + " thresholdBytes=" + thresholdBytes - + " }"); + + " networkType=" + networkType + + " subscriberId=" + subscriberId + + " thresholdBytes=" + thresholdBytes + + " }"); } - registerUsageCallback(template, networkType, thresholdBytes, callback, handler); + + final Executor executor = handler == null ? r -> r.run() : r -> handler.post(r); + + registerUsageCallback(template, thresholdBytes, executor, callback); } /** @@ -778,6 +837,26 @@ public class NetworkStatsManager { * Base class for usage callbacks. Should be extended by applications wanting notifications. */ public static abstract class UsageCallback { + /** + * Called when data usage has reached the given threshold. + * + * Called by {@code NetworkStatsService} when the registered threshold is reached. + * If a caller implements {@link #onThresholdReached(NetworkTemplate)}, the system + * will not call {@link #onThresholdReached(int, String)}. + * + * @param template The {@link NetworkTemplate} that associated with this callback. + * @hide + */ + @SystemApi(client = MODULE_LIBRARIES) + public void onThresholdReached(@NonNull NetworkTemplate template) { + // Backward compatibility for those who didn't override this function. + final int networkType = networkTypeForTemplate(template); + if (networkType != ConnectivityManager.TYPE_NONE) { + final String subscriberId = template.getSubscriberIds().isEmpty() ? null + : template.getSubscriberIds().iterator().next(); + onThresholdReached(networkType, subscriberId); + } + } /** * Called when data usage has reached the given threshold. @@ -788,6 +867,25 @@ public class NetworkStatsManager { * @hide used for internal bookkeeping */ private DataUsageRequest request; + + /** + * Get network type from a template if feasible. + * + * @param template the target {@link NetworkTemplate}. + * @return legacy network type, only supports for the types which is already supported in + * {@link #registerUsageCallback(int, String, long, UsageCallback, Handler)}. + * {@link ConnectivityManager#TYPE_NONE} for other types. + */ + private static int networkTypeForTemplate(@NonNull NetworkTemplate template) { + switch (template.getMatchRule()) { + case NetworkTemplate.MATCH_MOBILE: + return ConnectivityManager.TYPE_MOBILE; + case NetworkTemplate.MATCH_WIFI: + return ConnectivityManager.TYPE_WIFI; + default: + return ConnectivityManager.TYPE_NONE; + } + } } /** @@ -906,43 +1004,32 @@ public class NetworkStatsManager { } } - private static class CallbackHandler extends Handler { - private final int mNetworkType; - private final String mSubscriberId; - private UsageCallback mCallback; + private static class UsageCallbackWrapper extends IUsageCallback.Stub { + // Null if unregistered. + private volatile UsageCallback mCallback; + + private final Executor mExecutor; - CallbackHandler(Looper looper, int networkType, String subscriberId, - UsageCallback callback) { - super(looper); - mNetworkType = networkType; - mSubscriberId = subscriberId; + UsageCallbackWrapper(@NonNull Executor executor, @NonNull UsageCallback callback) { mCallback = callback; + mExecutor = executor; } @Override - public void handleMessage(Message message) { - DataUsageRequest request = - (DataUsageRequest) getObject(message, DataUsageRequest.PARCELABLE_KEY); - - switch (message.what) { - case CALLBACK_LIMIT_REACHED: { - if (mCallback != null) { - mCallback.onThresholdReached(mNetworkType, mSubscriberId); - } else { - Log.e(TAG, "limit reached with released callback for " + request); - } - break; - } - case CALLBACK_RELEASED: { - if (DBG) Log.d(TAG, "callback released for " + request); - mCallback = null; - break; - } + public void onThresholdReached(DataUsageRequest request) { + // Copy it to a local variable in case mCallback changed inside the if condition. + final UsageCallback callback = mCallback; + if (callback != null) { + mExecutor.execute(() -> callback.onThresholdReached(request.template)); + } else { + Log.e(TAG, "onThresholdReached with released callback for " + request); } } - private static Object getObject(Message msg, String key) { - return msg.getData().getParcelable(key); + @Override + public void onCallbackReleased(DataUsageRequest request) { + if (DBG) Log.d(TAG, "callback released for " + request); + mCallback = null; } } diff --git a/core/java/android/net/IInternalNetworkManagementListener.aidl b/packages/ConnectivityT/framework-t/src/android/net/IInternalNetworkManagementListener.aidl index 69cde3bd14e8..69cde3bd14e8 100644 --- a/core/java/android/net/IInternalNetworkManagementListener.aidl +++ b/packages/ConnectivityT/framework-t/src/android/net/IInternalNetworkManagementListener.aidl diff --git a/packages/ConnectivityT/framework-t/src/android/net/INetworkStatsService.aidl b/packages/ConnectivityT/framework-t/src/android/net/INetworkStatsService.aidl index a4babb543dbd..efe626d3c939 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/INetworkStatsService.aidl +++ b/packages/ConnectivityT/framework-t/src/android/net/INetworkStatsService.aidl @@ -24,6 +24,7 @@ import android.net.NetworkStats; import android.net.NetworkStatsHistory; import android.net.NetworkTemplate; import android.net.UnderlyingNetworkInfo; +import android.net.netstats.IUsageCallback; import android.net.netstats.provider.INetworkStatsProvider; import android.net.netstats.provider.INetworkStatsProviderCallback; import android.os.IBinder; @@ -49,14 +50,8 @@ interface INetworkStatsService { @UnsupportedAppUsage NetworkStats getDataLayerSnapshotForUid(int uid); - /** Get a detailed snapshot of stats since boot for all UIDs. - * - * <p>Results will not always be limited to stats on requiredIfaces when specified: stats for - * interfaces stacked on the specified interfaces, or for interfaces on which the specified - * interfaces are stacked on, will also be included. - * @param requiredIfaces Interface names to get data for, or {@link NetworkStats#INTERFACES_ALL}. - */ - NetworkStats getDetailedUidStats(in String[] requiredIfaces); + /** Get the transport NetworkStats for all UIDs since boot. */ + NetworkStats getUidStatsForTransport(int transport); /** Return set of any ifaces associated with mobile networks since boot. */ @UnsupportedAppUsage @@ -77,7 +72,7 @@ interface INetworkStatsService { /** Registers a callback on data usage. */ DataUsageRequest registerUsageCallback(String callingPackage, - in DataUsageRequest request, in Messenger messenger, in IBinder binder); + in DataUsageRequest request, in IUsageCallback callback); /** Unregisters a callback on data usage. */ void unregisterUsageRequest(in DataUsageRequest request); diff --git a/core/java/android/net/InternalNetworkManagementException.aidl b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkManagementException.aidl index dcce706989f6..dcce706989f6 100644 --- a/core/java/android/net/InternalNetworkManagementException.aidl +++ b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkManagementException.aidl diff --git a/core/java/android/net/InternalNetworkManagementException.java b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkManagementException.java index 7f4e403f2259..7f4e403f2259 100644 --- a/core/java/android/net/InternalNetworkManagementException.java +++ b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkManagementException.java diff --git a/core/java/android/net/InternalNetworkUpdateRequest.aidl b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkUpdateRequest.aidl index da00cb97afb4..da00cb97afb4 100644 --- a/core/java/android/net/InternalNetworkUpdateRequest.aidl +++ b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkUpdateRequest.aidl diff --git a/core/java/android/net/InternalNetworkUpdateRequest.java b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkUpdateRequest.java index f42c4b7c420d..f42c4b7c420d 100644 --- a/core/java/android/net/InternalNetworkUpdateRequest.java +++ b/packages/ConnectivityT/framework-t/src/android/net/InternalNetworkUpdateRequest.java diff --git a/packages/ConnectivityT/framework-t/src/android/net/IpSecAlgorithm.java b/packages/ConnectivityT/framework-t/src/android/net/IpSecAlgorithm.java index a84e7a9c6344..10a22ac360b1 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/IpSecAlgorithm.java +++ b/packages/ConnectivityT/framework-t/src/android/net/IpSecAlgorithm.java @@ -343,7 +343,7 @@ public final class IpSecAlgorithm implements Parcelable { // Load and validate the optional algorithm resource. Undefined or duplicate algorithms in // the resource are not allowed. final String[] resourceAlgos = systemResources.getStringArray( - com.android.internal.R.array.config_optionalIpSecAlgorithms); + android.R.array.config_optionalIpSecAlgorithms); for (String str : resourceAlgos) { if (!ALGO_TO_REQUIRED_FIRST_SDK.containsKey(str) || !enabledAlgos.add(str)) { // This error should be caught by CTS and never be thrown to API callers diff --git a/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentity.java b/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentity.java index 04d1d6885186..77fc17192c97 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentity.java +++ b/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentity.java @@ -16,18 +16,29 @@ package android.net; +import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; +import static android.net.ConnectivityManager.TYPE_MOBILE; import static android.net.ConnectivityManager.TYPE_WIFI; +import static android.net.NetworkTemplate.NETWORK_TYPE_ALL; +import android.annotation.IntDef; +import android.annotation.NonNull; import android.annotation.Nullable; +import android.annotation.SuppressLint; +import android.annotation.SystemApi; import android.content.Context; import android.net.wifi.WifiInfo; import android.service.NetworkIdentityProto; -import android.telephony.Annotation.NetworkType; +import android.telephony.Annotation; +import android.telephony.TelephonyManager; import android.util.proto.ProtoOutputStream; +import com.android.net.module.util.CollectionUtils; import com.android.net.module.util.NetworkCapabilitiesUtils; import com.android.net.module.util.NetworkIdentityUtils; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; import java.util.ArrayList; import java.util.Objects; @@ -37,11 +48,24 @@ import java.util.Objects; * * @hide */ -public class NetworkIdentity implements Comparable<NetworkIdentity> { +@SystemApi(client = MODULE_LIBRARIES) +public class NetworkIdentity { private static final String TAG = "NetworkIdentity"; + /** @hide */ + // TODO: Remove this after migrating all callers to use + // {@link NetworkTemplate#NETWORK_TYPE_ALL} instead. public static final int SUBTYPE_COMBINED = -1; + /** @hide */ + @Retention(RetentionPolicy.SOURCE) + @IntDef(prefix = { "OEM_MANAGED_" }, flag = true, value = { + NetworkTemplate.OEM_MANAGED_NO, + NetworkTemplate.OEM_MANAGED_PAID, + NetworkTemplate.OEM_MANAGED_PRIVATE + }) + public @interface OemManaged{} + /** * Network has no {@code NetworkCapabilities#NET_CAPABILITY_OEM_*}. * @hide @@ -51,29 +75,32 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { * Network has {@link NetworkCapabilities#NET_CAPABILITY_OEM_PAID}. * @hide */ - public static final int OEM_PAID = 0x1; + public static final int OEM_PAID = 1 << 0; /** * Network has {@link NetworkCapabilities#NET_CAPABILITY_OEM_PRIVATE}. * @hide */ - public static final int OEM_PRIVATE = 0x2; + public static final int OEM_PRIVATE = 1 << 1; + + private static final long SUPPORTED_OEM_MANAGED_TYPES = OEM_PAID | OEM_PRIVATE; final int mType; - final int mSubType; + final int mRatType; final String mSubscriberId; - final String mNetworkId; + final String mWifiNetworkKey; final boolean mRoaming; final boolean mMetered; final boolean mDefaultNetwork; final int mOemManaged; + /** @hide */ public NetworkIdentity( - int type, int subType, String subscriberId, String networkId, boolean roaming, - boolean metered, boolean defaultNetwork, int oemManaged) { + int type, int ratType, @Nullable String subscriberId, @Nullable String wifiNetworkKey, + boolean roaming, boolean metered, boolean defaultNetwork, int oemManaged) { mType = type; - mSubType = subType; + mRatType = ratType; mSubscriberId = subscriberId; - mNetworkId = networkId; + mWifiNetworkKey = wifiNetworkKey; mRoaming = roaming; mMetered = metered; mDefaultNetwork = defaultNetwork; @@ -82,7 +109,7 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { @Override public int hashCode() { - return Objects.hash(mType, mSubType, mSubscriberId, mNetworkId, mRoaming, mMetered, + return Objects.hash(mType, mRatType, mSubscriberId, mWifiNetworkKey, mRoaming, mMetered, mDefaultNetwork, mOemManaged); } @@ -90,9 +117,9 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { public boolean equals(@Nullable Object obj) { if (obj instanceof NetworkIdentity) { final NetworkIdentity ident = (NetworkIdentity) obj; - return mType == ident.mType && mSubType == ident.mSubType && mRoaming == ident.mRoaming + return mType == ident.mType && mRatType == ident.mRatType && mRoaming == ident.mRoaming && Objects.equals(mSubscriberId, ident.mSubscriberId) - && Objects.equals(mNetworkId, ident.mNetworkId) + && Objects.equals(mWifiNetworkKey, ident.mWifiNetworkKey) && mMetered == ident.mMetered && mDefaultNetwork == ident.mDefaultNetwork && mOemManaged == ident.mOemManaged; @@ -104,18 +131,18 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { public String toString() { final StringBuilder builder = new StringBuilder("{"); builder.append("type=").append(mType); - builder.append(", subType="); - if (mSubType == SUBTYPE_COMBINED) { + builder.append(", ratType="); + if (mRatType == NETWORK_TYPE_ALL) { builder.append("COMBINED"); } else { - builder.append(mSubType); + builder.append(mRatType); } if (mSubscriberId != null) { builder.append(", subscriberId=") .append(NetworkIdentityUtils.scrubSubscriberId(mSubscriberId)); } - if (mNetworkId != null) { - builder.append(", networkId=").append(mNetworkId); + if (mWifiNetworkKey != null) { + builder.append(", wifiNetworkKey=").append(mWifiNetworkKey); } if (mRoaming) { builder.append(", ROAMING"); @@ -153,12 +180,13 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { } } + /** @hide */ public void dumpDebug(ProtoOutputStream proto, long tag) { final long start = proto.start(tag); proto.write(NetworkIdentityProto.TYPE, mType); - // Not dumping mSubType, subtypes are no longer supported. + // TODO: dump mRatType as well. proto.write(NetworkIdentityProto.ROAMING, mRoaming); proto.write(NetworkIdentityProto.METERED, mMetered); @@ -168,77 +196,99 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { proto.end(start); } + /** Get the network type of this instance. */ public int getType() { return mType; } - public int getSubType() { - return mSubType; + /** Get the Radio Access Technology(RAT) type of this instance. */ + public int getRatType() { + return mRatType; } + /** Get the Subscriber Id of this instance. */ + @Nullable public String getSubscriberId() { return mSubscriberId; } - public String getNetworkId() { - return mNetworkId; + /** Get the Wifi Network Key of this instance. See {@link WifiInfo#getNetworkKey()}. */ + @Nullable + public String getWifiNetworkKey() { + return mWifiNetworkKey; } + /** @hide */ + // TODO: Remove this function after all callers are removed. public boolean getRoaming() { return mRoaming; } + /** Return whether this network is roaming. */ + public boolean isRoaming() { + return mRoaming; + } + + /** @hide */ + // TODO: Remove this function after all callers are removed. public boolean getMetered() { return mMetered; } + /** Return whether this network is metered. */ + public boolean isMetered() { + return mMetered; + } + + /** @hide */ + // TODO: Remove this function after all callers are removed. public boolean getDefaultNetwork() { return mDefaultNetwork; } + /** Return whether this network is the default network. */ + public boolean isDefaultNetwork() { + return mDefaultNetwork; + } + + /** Get the OEM managed type of this instance. */ public int getOemManaged() { return mOemManaged; } /** - * Build a {@link NetworkIdentity} from the given {@link NetworkStateSnapshot} and - * {@code subType}, assuming that any mobile networks are using the current IMSI. - * The subType if applicable, should be set as one of the TelephonyManager.NETWORK_TYPE_* - * constants, or {@link android.telephony.TelephonyManager#NETWORK_TYPE_UNKNOWN} if not. + * Assemble a {@link NetworkIdentity} from the passed arguments. + * + * This methods builds an identity based on the capabilities of the network in the + * snapshot and other passed arguments. The identity is used as a key to record data usage. + * + * @param snapshot the snapshot of network state. See {@link NetworkStateSnapshot}. + * @param defaultNetwork whether the network is a default network. + * @param ratType the Radio Access Technology(RAT) type of the network. Or + * {@link TelephonyManager#NETWORK_TYPE_UNKNOWN} if not applicable. + * See {@code TelephonyManager.NETWORK_TYPE_*}. + * @hide + * @deprecated See {@link NetworkIdentity.Builder}. */ + // TODO: Remove this after all callers are migrated to use new Api. + @Deprecated + @NonNull public static NetworkIdentity buildNetworkIdentity(Context context, - NetworkStateSnapshot snapshot, boolean defaultNetwork, @NetworkType int subType) { - final int legacyType = snapshot.getLegacyType(); - - final String subscriberId = snapshot.getSubscriberId(); - String networkId = null; - boolean roaming = !snapshot.getNetworkCapabilities().hasCapability( - NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING); - boolean metered = !(snapshot.getNetworkCapabilities().hasCapability( - NetworkCapabilities.NET_CAPABILITY_NOT_METERED) - || snapshot.getNetworkCapabilities().hasCapability( - NetworkCapabilities.NET_CAPABILITY_TEMPORARILY_NOT_METERED)); - - final int oemManaged = getOemBitfield(snapshot.getNetworkCapabilities()); - - if (legacyType == TYPE_WIFI) { - final TransportInfo transportInfo = snapshot.getNetworkCapabilities() - .getTransportInfo(); - if (transportInfo instanceof WifiInfo) { - final WifiInfo info = (WifiInfo) transportInfo; - networkId = info != null ? info.getCurrentNetworkKey() : null; - } + @NonNull NetworkStateSnapshot snapshot, + boolean defaultNetwork, @Annotation.NetworkType int ratType) { + final NetworkIdentity.Builder builder = new NetworkIdentity.Builder() + .setNetworkStateSnapshot(snapshot).setDefaultNetwork(defaultNetwork); + if (snapshot.getLegacyType() == TYPE_MOBILE && ratType != NETWORK_TYPE_ALL) { + builder.setRatType(ratType); } - - return new NetworkIdentity(legacyType, subType, subscriberId, networkId, roaming, metered, - defaultNetwork, oemManaged); + return builder.build(); } /** * Builds a bitfield of {@code NetworkIdentity.OEM_*} based on {@link NetworkCapabilities}. * @hide */ - public static int getOemBitfield(NetworkCapabilities nc) { + public static int getOemBitfield(@NonNull NetworkCapabilities nc) { int oemManaged = OEM_NONE; if (nc.hasCapability(NetworkCapabilities.NET_CAPABILITY_OEM_PAID)) { @@ -251,30 +301,266 @@ public class NetworkIdentity implements Comparable<NetworkIdentity> { return oemManaged; } - @Override - public int compareTo(NetworkIdentity another) { - int res = Integer.compare(mType, another.mType); + /** @hide */ + public static int compare(@NonNull NetworkIdentity left, @NonNull NetworkIdentity right) { + Objects.requireNonNull(right); + int res = Integer.compare(left.mType, right.mType); if (res == 0) { - res = Integer.compare(mSubType, another.mSubType); + res = Integer.compare(left.mRatType, right.mRatType); } - if (res == 0 && mSubscriberId != null && another.mSubscriberId != null) { - res = mSubscriberId.compareTo(another.mSubscriberId); + if (res == 0 && left.mSubscriberId != null && right.mSubscriberId != null) { + res = left.mSubscriberId.compareTo(right.mSubscriberId); } - if (res == 0 && mNetworkId != null && another.mNetworkId != null) { - res = mNetworkId.compareTo(another.mNetworkId); + if (res == 0 && left.mWifiNetworkKey != null && right.mWifiNetworkKey != null) { + res = left.mWifiNetworkKey.compareTo(right.mWifiNetworkKey); } if (res == 0) { - res = Boolean.compare(mRoaming, another.mRoaming); + res = Boolean.compare(left.mRoaming, right.mRoaming); } if (res == 0) { - res = Boolean.compare(mMetered, another.mMetered); + res = Boolean.compare(left.mMetered, right.mMetered); } if (res == 0) { - res = Boolean.compare(mDefaultNetwork, another.mDefaultNetwork); + res = Boolean.compare(left.mDefaultNetwork, right.mDefaultNetwork); } if (res == 0) { - res = Integer.compare(mOemManaged, another.mOemManaged); + res = Integer.compare(left.mOemManaged, right.mOemManaged); } return res; } + + /** + * Builder class for {@link NetworkIdentity}. + */ + public static final class Builder { + // Need to be synchronized with ConnectivityManager. + // TODO: Use {@link ConnectivityManager#MAX_NETWORK_TYPE} when this file is in the module. + private static final int MAX_NETWORK_TYPE = 18; // TYPE_TEST + private static final int MIN_NETWORK_TYPE = TYPE_MOBILE; + + private int mType; + private int mRatType; + private String mSubscriberId; + private String mWifiNetworkKey; + private boolean mRoaming; + private boolean mMetered; + private boolean mDefaultNetwork; + private int mOemManaged; + + /** + * Creates a new Builder. + */ + public Builder() { + // Initialize with default values. Will be overwritten by setters. + mType = ConnectivityManager.TYPE_NONE; + mRatType = NetworkTemplate.NETWORK_TYPE_ALL; + mSubscriberId = null; + mWifiNetworkKey = null; + mRoaming = false; + mMetered = false; + mDefaultNetwork = false; + mOemManaged = NetworkTemplate.OEM_MANAGED_NO; + } + + /** + * Add an {@link NetworkStateSnapshot} into the {@link NetworkIdentity} instance. + * This is a useful shorthand that will read from the snapshot and set the + * following fields, if they are set in the snapshot : + * - type + * - subscriberId + * - roaming + * - metered + * - oemManaged + * - wifiNetworkKey + * + * @param snapshot The target {@link NetworkStateSnapshot} object. + * @return The builder object. + */ + @SuppressLint("MissingGetterMatchingBuilder") + @NonNull + public Builder setNetworkStateSnapshot(@NonNull NetworkStateSnapshot snapshot) { + setType(snapshot.getLegacyType()); + + setSubscriberId(snapshot.getSubscriberId()); + setRoaming(!snapshot.getNetworkCapabilities().hasCapability( + NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING)); + setMetered(!(snapshot.getNetworkCapabilities().hasCapability( + NetworkCapabilities.NET_CAPABILITY_NOT_METERED) + || snapshot.getNetworkCapabilities().hasCapability( + NetworkCapabilities.NET_CAPABILITY_TEMPORARILY_NOT_METERED))); + + setOemManaged(getOemBitfield(snapshot.getNetworkCapabilities())); + + if (mType == TYPE_WIFI) { + final TransportInfo transportInfo = snapshot.getNetworkCapabilities() + .getTransportInfo(); + if (transportInfo instanceof WifiInfo) { + final WifiInfo info = (WifiInfo) transportInfo; + setWifiNetworkKey(info.getNetworkKey()); + } + } + return this; + } + + /** + * Set the network type of the network. + * + * @param type the network type. See {@link ConnectivityManager#TYPE_*}. + * + * @return this builder. + */ + @NonNull + public Builder setType(int type) { + // Include TYPE_NONE for compatibility, type field might not be filled by some + // networks such as test networks. + if ((type < MIN_NETWORK_TYPE || MAX_NETWORK_TYPE < type) + && type != ConnectivityManager.TYPE_NONE) { + throw new IllegalArgumentException("Invalid network type: " + type); + } + mType = type; + return this; + } + + /** + * Set the Radio Access Technology(RAT) type of the network. + * + * No RAT type is specified by default. Call clearRatType to reset. + * + * @param ratType the Radio Access Technology(RAT) type if applicable. See + * {@code TelephonyManager.NETWORK_TYPE_*}. + * + * @return this builder. + */ + @NonNull + public Builder setRatType(@Annotation.NetworkType int ratType) { + if (!CollectionUtils.contains(TelephonyManager.getAllNetworkTypes(), ratType) + && ratType != TelephonyManager.NETWORK_TYPE_UNKNOWN + && ratType != NetworkTemplate.NETWORK_TYPE_5G_NSA) { + throw new IllegalArgumentException("Invalid ratType " + ratType); + } + mRatType = ratType; + return this; + } + + /** + * Clear the Radio Access Technology(RAT) type of the network. + * + * @return this builder. + */ + @NonNull + public Builder clearRatType() { + mRatType = NetworkTemplate.NETWORK_TYPE_ALL; + return this; + } + + /** + * Set the Subscriber Id. + * + * @param subscriberId the Subscriber Id of the network. Or null if not applicable. + * @return this builder. + */ + @NonNull + public Builder setSubscriberId(@Nullable String subscriberId) { + mSubscriberId = subscriberId; + return this; + } + + /** + * Set the Wifi Network Key. + * + * @param wifiNetworkKey Wifi Network Key of the network, + * see {@link WifiInfo#getNetworkKey()}. + * Or null if not applicable. + * @return this builder. + */ + @NonNull + public Builder setWifiNetworkKey(@Nullable String wifiNetworkKey) { + mWifiNetworkKey = wifiNetworkKey; + return this; + } + + /** + * Set whether this network is roaming. + * + * This field is false by default. Call with false to reset. + * + * @param roaming the roaming status of the network. + * @return this builder. + */ + @NonNull + public Builder setRoaming(boolean roaming) { + mRoaming = roaming; + return this; + } + + /** + * Set whether this network is metered. + * + * This field is false by default. Call with false to reset. + * + * @param metered the meteredness of the network. + * @return this builder. + */ + @NonNull + public Builder setMetered(boolean metered) { + mMetered = metered; + return this; + } + + /** + * Set whether this network is the default network. + * + * This field is false by default. Call with false to reset. + * + * @param defaultNetwork the default network status of the network. + * @return this builder. + */ + @NonNull + public Builder setDefaultNetwork(boolean defaultNetwork) { + mDefaultNetwork = defaultNetwork; + return this; + } + + /** + * Set the OEM managed type. + * + * @param oemManaged Type of OEM managed network or unmanaged networks. + * See {@code NetworkTemplate#OEM_MANAGED_*}. + * @return this builder. + */ + @NonNull + public Builder setOemManaged(@OemManaged int oemManaged) { + // Assert input does not contain illegal oemManage bits. + if ((~SUPPORTED_OEM_MANAGED_TYPES & oemManaged) != 0) { + throw new IllegalArgumentException("Invalid value for OemManaged : " + oemManaged); + } + mOemManaged = oemManaged; + return this; + } + + private void ensureValidParameters() { + // Assert non-mobile network cannot have a ratType. + if (mType != TYPE_MOBILE && mRatType != NetworkTemplate.NETWORK_TYPE_ALL) { + throw new IllegalArgumentException( + "Invalid ratType " + mRatType + " for type " + mType); + } + + // Assert non-wifi network cannot have a wifi network key. + if (mType != TYPE_WIFI && mWifiNetworkKey != null) { + throw new IllegalArgumentException("Invalid wifi network key for type " + mType); + } + } + + /** + * Builds the instance of the {@link NetworkIdentity}. + * + * @return the built instance of {@link NetworkIdentity}. + */ + @NonNull + public NetworkIdentity build() { + ensureValidParameters(); + return new NetworkIdentity(mType, mRatType, mSubscriberId, mWifiNetworkKey, + mRoaming, mMetered, mDefaultNetwork, mOemManaged); + } + } } diff --git a/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentitySet.java b/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentitySet.java index abbebef85c8f..dfa347f6f12b 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentitySet.java +++ b/packages/ConnectivityT/framework-t/src/android/net/NetworkIdentitySet.java @@ -18,6 +18,7 @@ package android.net; import static android.net.ConnectivityManager.TYPE_MOBILE; +import android.annotation.NonNull; import android.service.NetworkIdentitySetProto; import android.util.proto.ProtoOutputStream; @@ -25,6 +26,8 @@ import java.io.DataInput; import java.io.DataOutput; import java.io.IOException; import java.util.HashSet; +import java.util.Objects; +import java.util.Set; /** * Identity of a {@code iface}, defined by the set of {@link NetworkIdentity} @@ -32,8 +35,7 @@ import java.util.HashSet; * * @hide */ -public class NetworkIdentitySet extends HashSet<NetworkIdentity> implements - Comparable<NetworkIdentitySet> { +public class NetworkIdentitySet extends HashSet<NetworkIdentity> { private static final int VERSION_INIT = 1; private static final int VERSION_ADD_ROAMING = 2; private static final int VERSION_ADD_NETWORK_ID = 3; @@ -41,9 +43,19 @@ public class NetworkIdentitySet extends HashSet<NetworkIdentity> implements private static final int VERSION_ADD_DEFAULT_NETWORK = 5; private static final int VERSION_ADD_OEM_MANAGED_NETWORK = 6; + /** + * Construct a {@link NetworkIdentitySet} object. + */ public NetworkIdentitySet() { + super(); } + /** @hide */ + public NetworkIdentitySet(@NonNull Set<NetworkIdentity> ident) { + super(ident); + } + + /** @hide */ public NetworkIdentitySet(DataInput in) throws IOException { final int version = in.readInt(); final int size = in.readInt(); @@ -52,7 +64,7 @@ public class NetworkIdentitySet extends HashSet<NetworkIdentity> implements final int ignored = in.readInt(); } final int type = in.readInt(); - final int subType = in.readInt(); + final int ratType = in.readInt(); final String subscriberId = readOptionalString(in); final String networkId; if (version >= VERSION_ADD_NETWORK_ID) { @@ -91,63 +103,73 @@ public class NetworkIdentitySet extends HashSet<NetworkIdentity> implements oemNetCapabilities = NetworkIdentity.OEM_NONE; } - add(new NetworkIdentity(type, subType, subscriberId, networkId, roaming, metered, + add(new NetworkIdentity(type, ratType, subscriberId, networkId, roaming, metered, defaultNetwork, oemNetCapabilities)); } } /** * Method to serialize this object into a {@code DataOutput}. + * @hide */ public void writeToStream(DataOutput out) throws IOException { out.writeInt(VERSION_ADD_OEM_MANAGED_NETWORK); out.writeInt(size()); for (NetworkIdentity ident : this) { out.writeInt(ident.getType()); - out.writeInt(ident.getSubType()); + out.writeInt(ident.getRatType()); writeOptionalString(out, ident.getSubscriberId()); - writeOptionalString(out, ident.getNetworkId()); - out.writeBoolean(ident.getRoaming()); - out.writeBoolean(ident.getMetered()); - out.writeBoolean(ident.getDefaultNetwork()); + writeOptionalString(out, ident.getWifiNetworkKey()); + out.writeBoolean(ident.isRoaming()); + out.writeBoolean(ident.isMetered()); + out.writeBoolean(ident.isDefaultNetwork()); out.writeInt(ident.getOemManaged()); } } - /** @return whether any {@link NetworkIdentity} in this set is considered metered. */ + /** + * @return whether any {@link NetworkIdentity} in this set is considered metered. + * @hide + */ public boolean isAnyMemberMetered() { if (isEmpty()) { return false; } for (NetworkIdentity ident : this) { - if (ident.getMetered()) { + if (ident.isMetered()) { return true; } } return false; } - /** @return whether any {@link NetworkIdentity} in this set is considered roaming. */ + /** + * @return whether any {@link NetworkIdentity} in this set is considered roaming. + * @hide + */ public boolean isAnyMemberRoaming() { if (isEmpty()) { return false; } for (NetworkIdentity ident : this) { - if (ident.getRoaming()) { + if (ident.isRoaming()) { return true; } } return false; } - /** @return whether any {@link NetworkIdentity} in this set is considered on the default - network. */ + /** + * @return whether any {@link NetworkIdentity} in this set is considered on the default + * network. + * @hide + */ public boolean areAllMembersOnDefaultNetwork() { if (isEmpty()) { return true; } for (NetworkIdentity ident : this) { - if (!ident.getDefaultNetwork()) { + if (!ident.isDefaultNetwork()) { return false; } } @@ -171,18 +193,20 @@ public class NetworkIdentitySet extends HashSet<NetworkIdentity> implements } } - @Override - public int compareTo(NetworkIdentitySet another) { - if (isEmpty()) return -1; - if (another.isEmpty()) return 1; + public static int compare(@NonNull NetworkIdentitySet left, @NonNull NetworkIdentitySet right) { + Objects.requireNonNull(left); + Objects.requireNonNull(right); + if (left.isEmpty()) return -1; + if (right.isEmpty()) return 1; - final NetworkIdentity ident = iterator().next(); - final NetworkIdentity anotherIdent = another.iterator().next(); - return ident.compareTo(anotherIdent); + final NetworkIdentity leftIdent = left.iterator().next(); + final NetworkIdentity rightIdent = right.iterator().next(); + return NetworkIdentity.compare(leftIdent, rightIdent); } /** * Method to dump this object into proto debug file. + * @hide */ public void dumpDebug(ProtoOutputStream proto, long tag) { final long start = proto.start(tag); diff --git a/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsCollection.java b/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsCollection.java index 9f9d73f88851..735c44d5c87e 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsCollection.java +++ b/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsCollection.java @@ -16,6 +16,7 @@ package android.net; +import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; import static android.net.NetworkStats.DEFAULT_NETWORK_NO; import static android.net.NetworkStats.DEFAULT_NETWORK_YES; import static android.net.NetworkStats.IFACE_ALL; @@ -32,6 +33,10 @@ import static android.text.format.DateUtils.WEEK_IN_MILLIS; import static com.android.net.module.util.NetworkStatsUtils.multiplySafeByRational; +import android.annotation.NonNull; +import android.annotation.Nullable; +import android.annotation.SystemApi; +import android.net.NetworkStatsHistory.Entry; import android.os.Binder; import android.service.NetworkStatsCollectionKeyProto; import android.service.NetworkStatsCollectionProto; @@ -69,7 +74,10 @@ import java.util.ArrayList; import java.util.Collections; import java.util.HashMap; import java.util.Iterator; +import java.util.List; +import java.util.Map; import java.util.Objects; +import java.util.Set; /** * Collection of {@link NetworkStatsHistory}, stored based on combined key of @@ -77,6 +85,7 @@ import java.util.Objects; * * @hide */ +@SystemApi(client = MODULE_LIBRARIES) public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.Writer { private static final String TAG = NetworkStatsCollection.class.getSimpleName(); /** File header magic number: "ANET" */ @@ -100,15 +109,23 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W private long mTotalBytes; private boolean mDirty; + /** + * Construct a {@link NetworkStatsCollection} object. + * + * @param bucketDuration duration of the buckets in this object, in milliseconds. + * @hide + */ public NetworkStatsCollection(long bucketDuration) { mBucketDuration = bucketDuration; reset(); } + /** @hide */ public void clear() { reset(); } + /** @hide */ public void reset() { mStats.clear(); mStartMillis = Long.MAX_VALUE; @@ -117,6 +134,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W mDirty = false; } + /** @hide */ public long getStartMillis() { return mStartMillis; } @@ -124,6 +142,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W /** * Return first atomic bucket in this collection, which is more conservative * than {@link #mStartMillis}. + * @hide */ public long getFirstAtomicBucketMillis() { if (mStartMillis == Long.MAX_VALUE) { @@ -133,26 +152,32 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } } + /** @hide */ public long getEndMillis() { return mEndMillis; } + /** @hide */ public long getTotalBytes() { return mTotalBytes; } + /** @hide */ public boolean isDirty() { return mDirty; } + /** @hide */ public void clearDirty() { mDirty = false; } + /** @hide */ public boolean isEmpty() { return mStartMillis == Long.MAX_VALUE && mEndMillis == Long.MIN_VALUE; } + /** @hide */ @VisibleForTesting public long roundUp(long time) { if (time == Long.MIN_VALUE || time == Long.MAX_VALUE @@ -168,6 +193,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } } + /** @hide */ @VisibleForTesting public long roundDown(long time) { if (time == Long.MIN_VALUE || time == Long.MAX_VALUE @@ -182,10 +208,12 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } } + /** @hide */ public int[] getRelevantUids(@NetworkStatsAccess.Level int accessLevel) { return getRelevantUids(accessLevel, Binder.getCallingUid()); } + /** @hide */ public int[] getRelevantUids(@NetworkStatsAccess.Level int accessLevel, final int callerUid) { final ArrayList<Integer> uids = new ArrayList<>(); @@ -206,6 +234,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W /** * Combine all {@link NetworkStatsHistory} in this collection which match * the requested parameters. + * @hide */ public NetworkStatsHistory getHistory(NetworkTemplate template, SubscriptionPlan augmentPlan, int uid, int set, int tag, int fields, long start, long end, @@ -331,6 +360,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W * @param end - end of the range, timestamp in milliseconds since the epoch. * @param accessLevel - caller access level. * @param callerUid - caller UID. + * @hide */ public NetworkStats getSummary(NetworkTemplate template, long start, long end, @NetworkStatsAccess.Level int accessLevel, int callerUid) { @@ -377,6 +407,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W /** * Record given {@link android.net.NetworkStats.Entry} into this collection. + * @hide */ public void recordData(NetworkIdentitySet ident, int uid, int set, int tag, long start, long end, NetworkStats.Entry entry) { @@ -387,8 +418,12 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W /** * Record given {@link NetworkStatsHistory} into this collection. + * + * @hide */ - private void recordHistory(Key key, NetworkStatsHistory history) { + public void recordHistory(@NonNull Key key, @NonNull NetworkStatsHistory history) { + Objects.requireNonNull(key); + Objects.requireNonNull(history); if (history.size() == 0) return; noteRecordedHistory(history.getStart(), history.getEnd(), history.getTotalBytes()); @@ -403,8 +438,11 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W /** * Record all {@link NetworkStatsHistory} contained in the given collection * into this collection. + * + * @hide */ - public void recordCollection(NetworkStatsCollection another) { + public void recordCollection(@NonNull NetworkStatsCollection another) { + Objects.requireNonNull(another); for (int i = 0; i < another.mStats.size(); i++) { final Key key = another.mStats.keyAt(i); final NetworkStatsHistory value = another.mStats.valueAt(i); @@ -433,6 +471,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } } + /** @hide */ @Override public void read(InputStream in) throws IOException { read((DataInput) new DataInputStream(in)); @@ -472,6 +511,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } } + /** @hide */ @Override public void write(OutputStream out) throws IOException { write((DataOutput) new DataOutputStream(out)); @@ -514,6 +554,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W * See {@code NetworkStatsService#maybeUpgradeLegacyStatsLocked}. * * @deprecated + * @hide */ @Deprecated public void readLegacyNetwork(File file) throws IOException { @@ -559,6 +600,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W * See {@code NetworkStatsService#maybeUpgradeLegacyStatsLocked}. * * @deprecated + * @hide */ @Deprecated public void readLegacyUid(File file, boolean onlyTags) throws IOException { @@ -629,6 +671,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W * Remove any {@link NetworkStatsHistory} attributed to the requested UID, * moving any {@link NetworkStats#TAG_NONE} series to * {@link TrafficStats#UID_REMOVED}. + * @hide */ public void removeUids(int[] uids) { final ArrayList<Key> knownKeys = new ArrayList<>(); @@ -665,10 +708,11 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W private ArrayList<Key> getSortedKeys() { final ArrayList<Key> keys = new ArrayList<>(); keys.addAll(mStats.keySet()); - Collections.sort(keys); + Collections.sort(keys, (left, right) -> Key.compare(left, right)); return keys; } + /** @hide */ public void dump(IndentingPrintWriter pw) { for (Key key : getSortedKeys()) { pw.print("ident="); pw.print(key.ident.toString()); @@ -683,6 +727,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } } + /** @hide */ public void dumpDebug(ProtoOutputStream proto, long tag) { final long start = proto.start(tag); @@ -706,6 +751,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W proto.end(start); } + /** @hide */ public void dumpCheckin(PrintWriter pw, long start, long end) { dumpCheckin(pw, start, end, NetworkTemplate.buildTemplateMobileWildcard(), "cell"); dumpCheckin(pw, start, end, NetworkTemplate.buildTemplateWifiWildcard(), "wifi"); @@ -768,16 +814,102 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W return false; } - private static class Key implements Comparable<Key> { + /** + * Get the all historical stats of the collection {@link NetworkStatsCollection}. + * + * @return All {@link NetworkStatsHistory} in this collection. + */ + @NonNull + public Map<Key, NetworkStatsHistory> getEntries() { + return new ArrayMap(mStats); + } + + /** + * Builder class for {@link NetworkStatsCollection}. + */ + public static final class Builder { + private final long mBucketDuration; + private final ArrayMap<Key, NetworkStatsHistory> mEntries = new ArrayMap<>(); + + /** + * Creates a new Builder with given bucket duration. + * + * @param bucketDuration Duration of the buckets of the object, in milliseconds. + */ + public Builder(long bucketDuration) { + mBucketDuration = bucketDuration; + } + + /** + * Add association of the history with the specified key in this map. + * + * @param key The object used to identify a network, see {@link Key}. + * @param history {@link NetworkStatsHistory} instance associated to the given {@link Key}. + * @return The builder object. + */ + @NonNull + public NetworkStatsCollection.Builder addEntry(@NonNull Key key, + @NonNull NetworkStatsHistory history) { + Objects.requireNonNull(key); + Objects.requireNonNull(history); + final List<Entry> historyEntries = history.getEntries(); + + final NetworkStatsHistory.Builder historyBuilder = + new NetworkStatsHistory.Builder(mBucketDuration, historyEntries.size()); + for (Entry entry : historyEntries) { + historyBuilder.addEntry(entry); + } + + mEntries.put(key, historyBuilder.build()); + return this; + } + + /** + * Builds the instance of the {@link NetworkStatsCollection}. + * + * @return the built instance of {@link NetworkStatsCollection}. + */ + @NonNull + public NetworkStatsCollection build() { + final NetworkStatsCollection collection = new NetworkStatsCollection(mBucketDuration); + for (int i = 0; i < mEntries.size(); i++) { + collection.recordHistory(mEntries.keyAt(i), mEntries.valueAt(i)); + } + return collection; + } + } + + /** + * the identifier that associate with the {@link NetworkStatsHistory} object to identify + * a certain record in the {@link NetworkStatsCollection} object. + */ + public static class Key { + /** @hide */ public final NetworkIdentitySet ident; + /** @hide */ public final int uid; + /** @hide */ public final int set; + /** @hide */ public final int tag; private final int mHashCode; - Key(NetworkIdentitySet ident, int uid, int set, int tag) { - this.ident = ident; + /** + * Construct a {@link Key} object. + * + * @param ident a Set of {@link NetworkIdentity} that associated with the record. + * @param uid Uid of the record. + * @param set Set of the record, see {@code NetworkStats#SET_*}. + * @param tag Tag of the record, see {@link TrafficStats#setThreadStatsTag(int)}. + */ + public Key(@NonNull Set<NetworkIdentity> ident, int uid, int set, int tag) { + this(new NetworkIdentitySet(Objects.requireNonNull(ident)), uid, set, tag); + } + + /** @hide */ + public Key(@NonNull NetworkIdentitySet ident, int uid, int set, int tag) { + this.ident = Objects.requireNonNull(ident); this.uid = uid; this.set = set; this.tag = tag; @@ -790,7 +922,7 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W } @Override - public boolean equals(Object obj) { + public boolean equals(@Nullable Object obj) { if (obj instanceof Key) { final Key key = (Key) obj; return uid == key.uid && set == key.set && tag == key.tag @@ -799,20 +931,22 @@ public class NetworkStatsCollection implements FileRotator.Reader, FileRotator.W return false; } - @Override - public int compareTo(Key another) { + /** @hide */ + public static int compare(@NonNull Key left, @NonNull Key right) { + Objects.requireNonNull(left); + Objects.requireNonNull(right); int res = 0; - if (ident != null && another.ident != null) { - res = ident.compareTo(another.ident); + if (left.ident != null && right.ident != null) { + res = NetworkIdentitySet.compare(left.ident, right.ident); } if (res == 0) { - res = Integer.compare(uid, another.uid); + res = Integer.compare(left.uid, right.uid); } if (res == 0) { - res = Integer.compare(set, another.set); + res = Integer.compare(left.set, right.set); } if (res == 0) { - res = Integer.compare(tag, another.tag); + res = Integer.compare(left.tag, right.tag); } return res; } diff --git a/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsHistory.java b/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsHistory.java index 428bc6df266a..78c137073aaa 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsHistory.java +++ b/packages/ConnectivityT/framework-t/src/android/net/NetworkStatsHistory.java @@ -16,6 +16,7 @@ package android.net; +import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; import static android.net.NetworkStats.IFACE_ALL; import static android.net.NetworkStats.SET_DEFAULT; import static android.net.NetworkStats.TAG_NONE; @@ -30,6 +31,8 @@ import static android.text.format.DateUtils.SECOND_IN_MILLIS; import static com.android.net.module.util.NetworkStatsUtils.multiplySafeByRational; +import android.annotation.NonNull; +import android.annotation.SystemApi; import android.compat.annotation.UnsupportedAppUsage; import android.os.Build; import android.os.Parcel; @@ -50,7 +53,9 @@ import java.io.DataOutput; import java.io.IOException; import java.io.PrintWriter; import java.net.ProtocolException; +import java.util.ArrayList; import java.util.Arrays; +import java.util.List; import java.util.Random; /** @@ -64,18 +69,25 @@ import java.util.Random; * * @hide */ -public class NetworkStatsHistory implements Parcelable { +@SystemApi(client = MODULE_LIBRARIES) +public final class NetworkStatsHistory implements Parcelable { private static final int VERSION_INIT = 1; private static final int VERSION_ADD_PACKETS = 2; private static final int VERSION_ADD_ACTIVE = 3; + /** @hide */ public static final int FIELD_ACTIVE_TIME = 0x01; + /** @hide */ public static final int FIELD_RX_BYTES = 0x02; + /** @hide */ public static final int FIELD_RX_PACKETS = 0x04; + /** @hide */ public static final int FIELD_TX_BYTES = 0x08; + /** @hide */ public static final int FIELD_TX_PACKETS = 0x10; + /** @hide */ public static final int FIELD_OPERATIONS = 0x20; - + /** @hide */ public static final int FIELD_ALL = 0xFFFFFFFF; private long bucketDuration; @@ -89,34 +101,171 @@ public class NetworkStatsHistory implements Parcelable { private long[] operations; private long totalBytes; - public static class Entry { + /** @hide */ + public NetworkStatsHistory(long bucketDuration, long[] bucketStart, long[] activeTime, + long[] rxBytes, long[] rxPackets, long[] txBytes, long[] txPackets, + long[] operations, int bucketCount, long totalBytes) { + this.bucketDuration = bucketDuration; + this.bucketStart = bucketStart; + this.activeTime = activeTime; + this.rxBytes = rxBytes; + this.rxPackets = rxPackets; + this.txBytes = txBytes; + this.txPackets = txPackets; + this.operations = operations; + this.bucketCount = bucketCount; + this.totalBytes = totalBytes; + } + + /** + * An instance to represent a single record in a {@link NetworkStatsHistory} object. + */ + public static final class Entry { + /** @hide */ public static final long UNKNOWN = -1; + /** @hide */ + // TODO: Migrate all callers to get duration from the history object and remove this field. @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public long bucketDuration; + /** @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public long bucketStart; + /** @hide */ public long activeTime; + /** @hide */ @UnsupportedAppUsage public long rxBytes; + /** @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public long rxPackets; + /** @hide */ @UnsupportedAppUsage public long txBytes; + /** @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public long txPackets; + /** @hide */ public long operations; + /** @hide */ + Entry() {} + + /** + * Construct a {@link Entry} instance to represent a single record in a + * {@link NetworkStatsHistory} object. + * + * @param bucketStart Start of period for this {@link Entry}, in milliseconds since the + * Unix epoch, see {@link java.lang.System#currentTimeMillis}. + * @param activeTime Active time for this {@link Entry}, in milliseconds. + * @param rxBytes Number of bytes received for this {@link Entry}. Statistics should + * represent the contents of IP packets, including IP headers. + * @param rxPackets Number of packets received for this {@link Entry}. Statistics should + * represent the contents of IP packets, including IP headers. + * @param txBytes Number of bytes transmitted for this {@link Entry}. Statistics should + * represent the contents of IP packets, including IP headers. + * @param txPackets Number of bytes transmitted for this {@link Entry}. Statistics should + * represent the contents of IP packets, including IP headers. + * @param operations count of network operations performed for this {@link Entry}. This can + * be used to derive bytes-per-operation. + */ + public Entry(long bucketStart, long activeTime, long rxBytes, + long rxPackets, long txBytes, long txPackets, long operations) { + this.bucketStart = bucketStart; + this.activeTime = activeTime; + this.rxBytes = rxBytes; + this.rxPackets = rxPackets; + this.txBytes = txBytes; + this.txPackets = txPackets; + this.operations = operations; + } + + /** + * Get start timestamp of the bucket's time interval, in milliseconds since the Unix epoch. + */ + public long getBucketStart() { + return bucketStart; + } + + /** + * Get active time of the bucket's time interval, in milliseconds. + */ + public long getActiveTime() { + return activeTime; + } + + /** Get number of bytes received for this {@link Entry}. */ + public long getRxBytes() { + return rxBytes; + } + + /** Get number of packets received for this {@link Entry}. */ + public long getRxPackets() { + return rxPackets; + } + + /** Get number of bytes transmitted for this {@link Entry}. */ + public long getTxBytes() { + return txBytes; + } + + /** Get number of packets transmitted for this {@link Entry}. */ + public long getTxPackets() { + return txPackets; + } + + /** Get count of network operations performed for this {@link Entry}. */ + public long getOperations() { + return operations; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o.getClass() != getClass()) return false; + Entry entry = (Entry) o; + return bucketStart == entry.bucketStart + && activeTime == entry.activeTime && rxBytes == entry.rxBytes + && rxPackets == entry.rxPackets && txBytes == entry.txBytes + && txPackets == entry.txPackets && operations == entry.operations; + } + + @Override + public int hashCode() { + return (int) (bucketStart * 2 + + activeTime * 3 + + rxBytes * 5 + + rxPackets * 7 + + txBytes * 11 + + txPackets * 13 + + operations * 17); + } + + @Override + public String toString() { + return "Entry{" + + "bucketStart=" + bucketStart + + ", activeTime=" + activeTime + + ", rxBytes=" + rxBytes + + ", rxPackets=" + rxPackets + + ", txBytes=" + txBytes + + ", txPackets=" + txPackets + + ", operations=" + operations + + "}"; + } } + /** @hide */ @UnsupportedAppUsage public NetworkStatsHistory(long bucketDuration) { this(bucketDuration, 10, FIELD_ALL); } + /** @hide */ public NetworkStatsHistory(long bucketDuration, int initialSize) { this(bucketDuration, initialSize, FIELD_ALL); } + /** @hide */ public NetworkStatsHistory(long bucketDuration, int initialSize, int fields) { this.bucketDuration = bucketDuration; bucketStart = new long[initialSize]; @@ -130,11 +279,13 @@ public class NetworkStatsHistory implements Parcelable { totalBytes = 0; } + /** @hide */ public NetworkStatsHistory(NetworkStatsHistory existing, long bucketDuration) { this(bucketDuration, existing.estimateResizeBuckets(bucketDuration)); recordEntireHistory(existing); } + /** @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public NetworkStatsHistory(Parcel in) { bucketDuration = in.readLong(); @@ -150,7 +301,7 @@ public class NetworkStatsHistory implements Parcelable { } @Override - public void writeToParcel(Parcel out, int flags) { + public void writeToParcel(@NonNull Parcel out, int flags) { out.writeLong(bucketDuration); writeLongArray(out, bucketStart, bucketCount); writeLongArray(out, activeTime, bucketCount); @@ -162,6 +313,7 @@ public class NetworkStatsHistory implements Parcelable { out.writeLong(totalBytes); } + /** @hide */ public NetworkStatsHistory(DataInput in) throws IOException { final int version = in.readInt(); switch (version) { @@ -204,6 +356,7 @@ public class NetworkStatsHistory implements Parcelable { } } + /** @hide */ public void writeToStream(DataOutput out) throws IOException { out.writeInt(VERSION_ADD_ACTIVE); out.writeLong(bucketDuration); @@ -221,15 +374,18 @@ public class NetworkStatsHistory implements Parcelable { return 0; } + /** @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public int size() { return bucketCount; } + /** @hide */ public long getBucketDuration() { return bucketDuration; } + /** @hide */ @UnsupportedAppUsage public long getStart() { if (bucketCount > 0) { @@ -239,6 +395,7 @@ public class NetworkStatsHistory implements Parcelable { } } + /** @hide */ @UnsupportedAppUsage public long getEnd() { if (bucketCount > 0) { @@ -250,6 +407,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Return total bytes represented by this history. + * @hide */ public long getTotalBytes() { return totalBytes; @@ -258,6 +416,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Return index of bucket that contains or is immediately before the * requested time. + * @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public int getIndexBefore(long time) { @@ -273,6 +432,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Return index of bucket that contains or is immediately after the * requested time. + * @hide */ public int getIndexAfter(long time) { int index = Arrays.binarySearch(bucketStart, 0, bucketCount, time); @@ -286,6 +446,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Return specific stats entry. + * @hide */ @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) public Entry getValues(int i, Entry recycle) { @@ -301,6 +462,23 @@ public class NetworkStatsHistory implements Parcelable { return entry; } + /** + * Get List of {@link Entry} of the {@link NetworkStatsHistory} instance. + * + * @return + */ + @NonNull + public List<Entry> getEntries() { + // TODO: Return a wrapper that uses this list instead, to prevent the returned result + // from being changed. + final ArrayList<Entry> ret = new ArrayList<>(size()); + for (int i = 0; i < size(); i++) { + ret.add(getValues(i, null /* recycle */)); + } + return ret; + } + + /** @hide */ public void setValues(int i, Entry entry) { // Unwind old values if (rxBytes != null) totalBytes -= rxBytes[i]; @@ -322,6 +500,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Record that data traffic occurred in the given time range. Will * distribute across internal buckets, creating new buckets as needed. + * @hide */ @Deprecated public void recordData(long start, long end, long rxBytes, long txBytes) { @@ -332,6 +511,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Record that data traffic occurred in the given time range. Will * distribute across internal buckets, creating new buckets as needed. + * @hide */ public void recordData(long start, long end, NetworkStats.Entry entry) { long rxBytes = entry.rxBytes; @@ -392,6 +572,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Record an entire {@link NetworkStatsHistory} into this history. Usually * for combining together stats for external reporting. + * @hide */ @UnsupportedAppUsage public void recordEntireHistory(NetworkStatsHistory input) { @@ -402,6 +583,7 @@ public class NetworkStatsHistory implements Parcelable { * Record given {@link NetworkStatsHistory} into this history, copying only * buckets that atomically occur in the inclusive time range. Doesn't * interpolate across partial buckets. + * @hide */ public void recordHistory(NetworkStatsHistory input, long start, long end) { final NetworkStats.Entry entry = new NetworkStats.Entry( @@ -483,6 +665,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Clear all data stored in this object. + * @hide */ public void clear() { bucketStart = EmptyArray.LONG; @@ -498,9 +681,10 @@ public class NetworkStatsHistory implements Parcelable { /** * Remove buckets older than requested cutoff. + * @hide */ - @Deprecated public void removeBucketsBefore(long cutoff) { + // TODO: Consider use getIndexBefore. int i; for (i = 0; i < bucketCount; i++) { final long curStart = bucketStart[i]; @@ -522,7 +706,9 @@ public class NetworkStatsHistory implements Parcelable { if (operations != null) operations = Arrays.copyOfRange(operations, i, length); bucketCount -= i; - // TODO: subtract removed values from totalBytes + totalBytes = 0; + if (rxBytes != null) totalBytes += CollectionUtils.total(rxBytes); + if (txBytes != null) totalBytes += CollectionUtils.total(txBytes); } } @@ -536,6 +722,7 @@ public class NetworkStatsHistory implements Parcelable { * @param start - start of the range, timestamp in milliseconds since the epoch. * @param end - end of the range, timestamp in milliseconds since the epoch. * @param recycle - entry instance for performance, could be null. + * @hide */ @UnsupportedAppUsage public Entry getValues(long start, long end, Entry recycle) { @@ -550,6 +737,7 @@ public class NetworkStatsHistory implements Parcelable { * @param end - end of the range, timestamp in milliseconds since the epoch. * @param now - current timestamp in milliseconds since the epoch (wall clock). * @param recycle - entry instance for performance, could be null. + * @hide */ @UnsupportedAppUsage public Entry getValues(long start, long end, long now, Entry recycle) { @@ -613,6 +801,7 @@ public class NetworkStatsHistory implements Parcelable { /** * @deprecated only for temporary testing + * @hide */ @Deprecated public void generateRandom(long start, long end, long bytes) { @@ -631,6 +820,7 @@ public class NetworkStatsHistory implements Parcelable { /** * @deprecated only for temporary testing + * @hide */ @Deprecated public void generateRandom(long start, long end, long rxBytes, long rxPackets, long txBytes, @@ -660,12 +850,14 @@ public class NetworkStatsHistory implements Parcelable { } } + /** @hide */ public static long randomLong(Random r, long start, long end) { return (long) (start + (r.nextFloat() * (end - start))); } /** * Quickly determine if this history intersects with given window. + * @hide */ public boolean intersects(long start, long end) { final long dataStart = getStart(); @@ -677,6 +869,7 @@ public class NetworkStatsHistory implements Parcelable { return false; } + /** @hide */ public void dump(IndentingPrintWriter pw, boolean fullHistory) { pw.print("NetworkStatsHistory: bucketDuration="); pw.println(bucketDuration / SECOND_IN_MILLIS); @@ -700,6 +893,7 @@ public class NetworkStatsHistory implements Parcelable { pw.decreaseIndent(); } + /** @hide */ public void dumpCheckin(PrintWriter pw) { pw.print("d,"); pw.print(bucketDuration / SECOND_IN_MILLIS); @@ -717,6 +911,7 @@ public class NetworkStatsHistory implements Parcelable { } } + /** @hide */ public void dumpDebug(ProtoOutputStream proto, long tag) { final long start = proto.start(tag); @@ -776,6 +971,7 @@ public class NetworkStatsHistory implements Parcelable { if (array != null) array[i] += value; } + /** @hide */ public int estimateResizeBuckets(long newBucketDuration) { return (int) (size() * getBucketDuration() / newBucketDuration); } @@ -783,6 +979,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Utility methods for interacting with {@link DataInputStream} and * {@link DataOutputStream}, mostly dealing with writing partial arrays. + * @hide */ public static class DataStreamUtils { @Deprecated @@ -857,6 +1054,7 @@ public class NetworkStatsHistory implements Parcelable { /** * Utility methods for interacting with {@link Parcel} structures, mostly * dealing with writing partial arrays. + * @hide */ public static class ParcelUtils { public static long[] readLongArray(Parcel in) { @@ -884,4 +1082,80 @@ public class NetworkStatsHistory implements Parcelable { } } + /** + * Builder class for {@link NetworkStatsHistory}. + */ + public static final class Builder { + private final long mBucketDuration; + private final List<Long> mBucketStart; + private final List<Long> mActiveTime; + private final List<Long> mRxBytes; + private final List<Long> mRxPackets; + private final List<Long> mTxBytes; + private final List<Long> mTxPackets; + private final List<Long> mOperations; + + /** + * Creates a new Builder with given bucket duration and initial capacity to construct + * {@link NetworkStatsHistory} objects. + * + * @param bucketDuration Duration of the buckets of the object, in milliseconds. + * @param initialCapacity Estimated number of records. + */ + public Builder(long bucketDuration, int initialCapacity) { + mBucketDuration = bucketDuration; + mBucketStart = new ArrayList<>(initialCapacity); + mActiveTime = new ArrayList<>(initialCapacity); + mRxBytes = new ArrayList<>(initialCapacity); + mRxPackets = new ArrayList<>(initialCapacity); + mTxBytes = new ArrayList<>(initialCapacity); + mTxPackets = new ArrayList<>(initialCapacity); + mOperations = new ArrayList<>(initialCapacity); + } + + /** + * Add an {@link Entry} into the {@link NetworkStatsHistory} instance. + * + * @param entry The target {@link Entry} object. + * @return The builder object. + */ + @NonNull + public Builder addEntry(@NonNull Entry entry) { + mBucketStart.add(entry.bucketStart); + mActiveTime.add(entry.activeTime); + mRxBytes.add(entry.rxBytes); + mRxPackets.add(entry.rxPackets); + mTxBytes.add(entry.txBytes); + mTxPackets.add(entry.txPackets); + mOperations.add(entry.operations); + return this; + } + + private static long sum(@NonNull List<Long> list) { + long sum = 0; + for (long entry : list) { + sum += entry; + } + return sum; + } + + /** + * Builds the instance of the {@link NetworkStatsHistory}. + * + * @return the built instance of {@link NetworkStatsHistory}. + */ + @NonNull + public NetworkStatsHistory build() { + return new NetworkStatsHistory(mBucketDuration, + CollectionUtils.toLongArray(mBucketStart), + CollectionUtils.toLongArray(mActiveTime), + CollectionUtils.toLongArray(mRxBytes), + CollectionUtils.toLongArray(mRxPackets), + CollectionUtils.toLongArray(mTxBytes), + CollectionUtils.toLongArray(mTxPackets), + CollectionUtils.toLongArray(mOperations), + mBucketStart.size(), + sum(mRxBytes) + sum(mTxBytes)); + } + } } diff --git a/packages/ConnectivityT/framework-t/src/android/net/NetworkTemplate.java b/packages/ConnectivityT/framework-t/src/android/net/NetworkTemplate.java index e9084b019668..dba39913300c 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/NetworkTemplate.java +++ b/packages/ConnectivityT/framework-t/src/android/net/NetworkTemplate.java @@ -263,7 +263,7 @@ public final class NetworkTemplate implements Parcelable { * Template to match {@link ConnectivityManager#TYPE_WIFI} networks with the * given key of the wifi network. * - * @param wifiNetworkKey key of the wifi network. see {@link WifiInfo#getCurrentNetworkKey()} + * @param wifiNetworkKey key of the wifi network. see {@link WifiInfo#getNetworkKey()} * to know details about the key. * @hide */ @@ -283,7 +283,7 @@ public final class NetworkTemplate implements Parcelable { * Call with {@link #WIFI_NETWORK_KEY_ALL} for {@code wifiNetworkKey} to get result regardless * of key of the wifi network. * - * @param wifiNetworkKey key of the wifi network. see {@link WifiInfo#getCurrentNetworkKey()} + * @param wifiNetworkKey key of the wifi network. see {@link WifiInfo#getNetworkKey()} * to know details about the key. * @param subscriberId the IMSI associated to this wifi network. * @@ -364,7 +364,7 @@ public final class NetworkTemplate implements Parcelable { private final int mMetered; private final int mRoaming; private final int mDefaultNetwork; - private final int mSubType; + private final int mRatType; /** * The subscriber Id match rule defines how the template should match networks with * specific subscriberId(s). See NetworkTemplate#SUBSCRIBER_ID_MATCH_RULE_* for more detail. @@ -413,18 +413,18 @@ public final class NetworkTemplate implements Parcelable { /** @hide */ // TODO: Remove it after updating all of the caller. public NetworkTemplate(int matchRule, String subscriberId, String[] matchSubscriberIds, - String wifiNetworkKey, int metered, int roaming, int defaultNetwork, int subType, + String wifiNetworkKey, int metered, int roaming, int defaultNetwork, int ratType, int oemManaged) { this(matchRule, subscriberId, matchSubscriberIds, wifiNetworkKey != null ? new String[] { wifiNetworkKey } : new String[0], - metered, roaming, defaultNetwork, subType, oemManaged, + metered, roaming, defaultNetwork, ratType, oemManaged, NetworkStatsUtils.SUBSCRIBER_ID_MATCH_RULE_EXACT); } /** @hide */ public NetworkTemplate(int matchRule, String subscriberId, String[] matchSubscriberIds, String[] matchWifiNetworkKeys, int metered, int roaming, - int defaultNetwork, int subType, int oemManaged, int subscriberIdMatchRule) { + int defaultNetwork, int ratType, int oemManaged, int subscriberIdMatchRule) { Objects.requireNonNull(matchWifiNetworkKeys); mMatchRule = matchRule; mSubscriberId = subscriberId; @@ -435,7 +435,7 @@ public final class NetworkTemplate implements Parcelable { mMetered = metered; mRoaming = roaming; mDefaultNetwork = defaultNetwork; - mSubType = subType; + mRatType = ratType; mOemManaged = oemManaged; mSubscriberIdMatchRule = subscriberIdMatchRule; checkValidSubscriberIdMatchRule(matchRule, subscriberIdMatchRule); @@ -453,7 +453,7 @@ public final class NetworkTemplate implements Parcelable { mMetered = in.readInt(); mRoaming = in.readInt(); mDefaultNetwork = in.readInt(); - mSubType = in.readInt(); + mRatType = in.readInt(); mOemManaged = in.readInt(); mSubscriberIdMatchRule = in.readInt(); } @@ -467,7 +467,7 @@ public final class NetworkTemplate implements Parcelable { dest.writeInt(mMetered); dest.writeInt(mRoaming); dest.writeInt(mDefaultNetwork); - dest.writeInt(mSubType); + dest.writeInt(mRatType); dest.writeInt(mOemManaged); dest.writeInt(mSubscriberIdMatchRule); } @@ -500,8 +500,8 @@ public final class NetworkTemplate implements Parcelable { builder.append(", defaultNetwork=").append(NetworkStats.defaultNetworkToString( mDefaultNetwork)); } - if (mSubType != NETWORK_TYPE_ALL) { - builder.append(", subType=").append(mSubType); + if (mRatType != NETWORK_TYPE_ALL) { + builder.append(", ratType=").append(mRatType); } if (mOemManaged != OEM_MANAGED_ALL) { builder.append(", oemManaged=").append(getOemManagedNames(mOemManaged)); @@ -514,7 +514,7 @@ public final class NetworkTemplate implements Parcelable { @Override public int hashCode() { return Objects.hash(mMatchRule, mSubscriberId, Arrays.hashCode(mMatchWifiNetworkKeys), - mMetered, mRoaming, mDefaultNetwork, mSubType, mOemManaged, mSubscriberIdMatchRule); + mMetered, mRoaming, mDefaultNetwork, mRatType, mOemManaged, mSubscriberIdMatchRule); } @Override @@ -526,7 +526,7 @@ public final class NetworkTemplate implements Parcelable { && mMetered == other.mMetered && mRoaming == other.mRoaming && mDefaultNetwork == other.mDefaultNetwork - && mSubType == other.mSubType + && mRatType == other.mRatType && mOemManaged == other.mOemManaged && mSubscriberIdMatchRule == other.mSubscriberIdMatchRule && Arrays.equals(mMatchWifiNetworkKeys, other.mMatchWifiNetworkKeys); @@ -593,7 +593,7 @@ public final class NetworkTemplate implements Parcelable { /** * Get the set of Wifi Network Keys of the template. - * See {@link WifiInfo#getCurrentNetworkKey()}. + * See {@link WifiInfo#getNetworkKey()}. */ @NonNull public Set<String> getWifiNetworkKeys() { @@ -635,7 +635,7 @@ public final class NetworkTemplate implements Parcelable { * Get the Radio Access Technology(RAT) type filter of the template. */ public int getRatType() { - return mSubType; + return mRatType; } /** @@ -652,7 +652,9 @@ public final class NetworkTemplate implements Parcelable { * * @hide */ - public boolean matches(NetworkIdentity ident) { + @SystemApi(client = MODULE_LIBRARIES) + public boolean matches(@NonNull NetworkIdentity ident) { + Objects.requireNonNull(ident); if (!matchesMetered(ident)) return false; if (!matchesRoaming(ident)) return false; if (!matchesDefaultNetwork(ident)) return false; @@ -708,8 +710,8 @@ public final class NetworkTemplate implements Parcelable { } private boolean matchesCollapsedRatType(NetworkIdentity ident) { - return mSubType == NETWORK_TYPE_ALL - || getCollapsedRatType(mSubType) == getCollapsedRatType(ident.mSubType); + return mRatType == NETWORK_TYPE_ALL + || getCollapsedRatType(mRatType) == getCollapsedRatType(ident.mRatType); } /** @@ -729,7 +731,7 @@ public final class NetworkTemplate implements Parcelable { * Returns true when the key matches, or when {@code mMatchWifiNetworkKeys} is * empty. * - * @param wifiNetworkKey key of the wifi network. see {@link WifiInfo#getCurrentNetworkKey()} + * @param wifiNetworkKey key of the wifi network. see {@link WifiInfo#getNetworkKey()} * to know details about the key. */ private boolean matchesWifiNetworkKey(@NonNull String wifiNetworkKey) { @@ -837,7 +839,7 @@ public final class NetworkTemplate implements Parcelable { switch (ident.mType) { case TYPE_WIFI: return matchesSubscriberId(ident.mSubscriberId) - && matchesWifiNetworkKey(ident.mNetworkId); + && matchesWifiNetworkKey(ident.mWifiNetworkKey); default: return false; } @@ -1059,9 +1061,9 @@ public final class NetworkTemplate implements Parcelable { * the intention of matching any Wifi Network Key. * * @param wifiNetworkKeys the list of Wifi Network Key, - * see {@link WifiInfo#getCurrentNetworkKey()}. + * see {@link WifiInfo#getNetworkKey()}. * Or an empty list to match all networks. - * Note that {@code getCurrentNetworkKey()} might get null key + * Note that {@code getNetworkKey()} might get null key * when wifi disconnects. However, the caller should never invoke * this function with a null Wifi Network Key since such statistics * never exists. diff --git a/packages/ConnectivityT/framework-t/src/android/net/TrafficStats.java b/packages/ConnectivityT/framework-t/src/android/net/TrafficStats.java index 1af32bf5524c..c2f0cdfb048c 100644 --- a/packages/ConnectivityT/framework-t/src/android/net/TrafficStats.java +++ b/packages/ConnectivityT/framework-t/src/android/net/TrafficStats.java @@ -16,8 +16,9 @@ package android.net; +import static android.annotation.SystemApi.Client.MODULE_LIBRARIES; + import android.annotation.NonNull; -import android.annotation.Nullable; import android.annotation.SuppressLint; import android.annotation.SystemApi; import android.annotation.TestApi; @@ -27,9 +28,10 @@ import android.app.usage.NetworkStatsManager; import android.compat.annotation.UnsupportedAppUsage; import android.content.Context; import android.media.MediaPlayer; +import android.os.Binder; import android.os.Build; -import android.os.IBinder; import android.os.RemoteException; +import android.util.Log; import com.android.server.NetworkManagementSocketTagger; @@ -37,8 +39,6 @@ import dalvik.system.SocketTagger; import java.io.FileDescriptor; import java.io.IOException; -import java.lang.reflect.InvocationTargetException; -import java.lang.reflect.Method; import java.net.DatagramSocket; import java.net.Socket; import java.net.SocketException; @@ -177,25 +177,12 @@ public class TrafficStats { @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P, trackingBug = 130143562) private synchronized static INetworkStatsService getStatsService() { if (sStatsService == null) { - sStatsService = getStatsBinder(); + throw new IllegalStateException("TrafficStats not initialized, uid=" + + Binder.getCallingUid()); } return sStatsService; } - @Nullable - private static INetworkStatsService getStatsBinder() { - try { - final Method getServiceMethod = Class.forName("android.os.ServiceManager") - .getDeclaredMethod("getService", new Class[]{String.class}); - final IBinder binder = (IBinder) getServiceMethod.invoke( - null, Context.NETWORK_STATS_SERVICE); - return INetworkStatsService.Stub.asInterface(binder); - } catch (NoSuchMethodException | ClassNotFoundException | IllegalAccessException - | InvocationTargetException e) { - throw new NullPointerException("Cannot get INetworkStatsService: " + e); - } - } - /** * Snapshot of {@link NetworkStats} when the currently active profiling * session started, or {@code null} if no session active. @@ -210,6 +197,45 @@ public class TrafficStats { private static final String LOOPBACK_IFACE = "lo"; /** + * Initialization {@link TrafficStats} with the context, to + * allow {@link TrafficStats} to fetch the needed binder. + * + * @param context a long-lived context, such as the application context or system + * server context. + * @hide + */ + @SystemApi(client = SystemApi.Client.MODULE_LIBRARIES) + @SuppressLint("VisiblySynchronized") + public static synchronized void init(@NonNull final Context context) { + if (sStatsService != null) { + throw new IllegalStateException("TrafficStats is already initialized, uid=" + + Binder.getCallingUid()); + } + final NetworkStatsManager statsManager = + context.getSystemService(NetworkStatsManager.class); + if (statsManager == null) { + // TODO: Currently Process.isSupplemental is not working yet, because it depends on + // process to run in a certain UID range, which is not true for now. Change this + // to Log.wtf once Process.isSupplemental is ready. + Log.e(TAG, "TrafficStats not initialized, uid=" + Binder.getCallingUid()); + return; + } + sStatsService = statsManager.getBinder(); + } + + /** + * Attach the socket tagger implementation to the current process, to + * get notified when a socket's {@link FileDescriptor} is assigned to + * a thread. See {@link SocketTagger#set(SocketTagger)}. + * + * @hide + */ + @SystemApi(client = MODULE_LIBRARIES) + public static void attachSocketTagger() { + NetworkManagementSocketTagger.install(); + } + + /** * Set active tag to use when accounting {@link Socket} traffic originating * from the current thread. Only one active tag per thread is supported. * <p> diff --git a/packages/ConnectivityT/framework-t/src/android/net/netstats/IUsageCallback.aidl b/packages/ConnectivityT/framework-t/src/android/net/netstats/IUsageCallback.aidl new file mode 100644 index 000000000000..4e8a5b23093a --- /dev/null +++ b/packages/ConnectivityT/framework-t/src/android/net/netstats/IUsageCallback.aidl @@ -0,0 +1,29 @@ +/* + * Copyright (C) 2022 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.net.netstats; + +import android.net.DataUsageRequest; + +/** + * Interface for NetworkStatsService to notify events to the callers of registerUsageCallback. + * + * @hide + */ +oneway interface IUsageCallback { + void onThresholdReached(in DataUsageRequest request); + void onCallbackReleased(in DataUsageRequest request); +} diff --git a/packages/ConnectivityT/service/Android.bp b/packages/ConnectivityT/service/Android.bp index b261e165a112..24bc91d91ef7 100644 --- a/packages/ConnectivityT/service/Android.bp +++ b/packages/ConnectivityT/service/Android.bp @@ -26,6 +26,8 @@ filegroup { srcs: [ "src/com/android/server/net/NetworkIdentity*.java", "src/com/android/server/net/NetworkStats*.java", + "src/com/android/server/net/BpfInterfaceMapUpdater.java", + "src/com/android/server/net/InterfaceMapValue.java", ], path: "src", visibility: [ @@ -66,6 +68,7 @@ filegroup { filegroup { name: "services.connectivity-ethernet-sources", srcs: [ + "src/com/android/server/net/DelayedDiskWrite.java", "src/com/android/server/net/IpConfigStore.java", ], path: "src", @@ -97,3 +100,28 @@ filegroup { "//packages/modules/Connectivity:__subpackages__", ], } + +cc_library_shared { + name: "libcom_android_net_module_util_jni", + min_sdk_version: "30", + cflags: [ + "-Wall", + "-Werror", + "-Wno-unused-parameter", + "-Wthread-safety", + ], + srcs: [ + "jni/onload.cpp", + ], + stl: "libc++_static", + static_libs: [ + "libnet_utils_device_common_bpfjni", + ], + shared_libs: [ + "liblog", + "libnativehelper", + ], + apex_available: [ + "//apex_available:platform", + ], +} diff --git a/packages/ConnectivityT/service/jni/onload.cpp b/packages/ConnectivityT/service/jni/onload.cpp new file mode 100644 index 000000000000..bca469756095 --- /dev/null +++ b/packages/ConnectivityT/service/jni/onload.cpp @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2022 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 <nativehelper/JNIHelp.h> +#include <log/log.h> + +namespace android { + +int register_com_android_net_module_util_BpfMap(JNIEnv* env, char const* class_name); + +extern "C" jint JNI_OnLoad(JavaVM* vm, void*) { + JNIEnv *env; + if (vm->GetEnv(reinterpret_cast<void**>(&env), JNI_VERSION_1_6) != JNI_OK) { + ALOGE("GetEnv failed"); + return JNI_ERR; + } + + if (register_com_android_net_module_util_BpfMap(env, + "com/android/net/module/util/BpfMap") < 0) return JNI_ERR; + + return JNI_VERSION_1_6; +} + +}; + diff --git a/packages/ConnectivityT/service/src/com/android/server/net/BpfInterfaceMapUpdater.java b/packages/ConnectivityT/service/src/com/android/server/net/BpfInterfaceMapUpdater.java new file mode 100644 index 000000000000..25c88eb6bdb2 --- /dev/null +++ b/packages/ConnectivityT/service/src/com/android/server/net/BpfInterfaceMapUpdater.java @@ -0,0 +1,139 @@ +/* + * Copyright (C) 2022 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.net; + +import android.content.Context; +import android.net.INetd; +import android.os.Handler; +import android.os.IBinder; +import android.os.RemoteException; +import android.os.ServiceSpecificException; +import android.system.ErrnoException; +import android.util.Log; + +import com.android.internal.annotations.VisibleForTesting; +import com.android.net.module.util.BaseNetdUnsolicitedEventListener; +import com.android.net.module.util.BpfMap; +import com.android.net.module.util.IBpfMap; +import com.android.net.module.util.InterfaceParams; +import com.android.net.module.util.Struct.U32; + +/** + * Monitor interface added (without removed) and right interface name and its index to bpf map. + */ +public class BpfInterfaceMapUpdater { + private static final String TAG = BpfInterfaceMapUpdater.class.getSimpleName(); + // This is current path but may be changed soon. + private static final String IFACE_INDEX_NAME_MAP_PATH = + "/sys/fs/bpf/map_netd_iface_index_name_map"; + private final IBpfMap<U32, InterfaceMapValue> mBpfMap; + private final INetd mNetd; + private final Handler mHandler; + private final Dependencies mDeps; + + public BpfInterfaceMapUpdater(Context ctx, Handler handler) { + this(ctx, handler, new Dependencies()); + } + + @VisibleForTesting + public BpfInterfaceMapUpdater(Context ctx, Handler handler, Dependencies deps) { + mDeps = deps; + mBpfMap = deps.getInterfaceMap(); + mNetd = deps.getINetd(ctx); + mHandler = handler; + } + + /** + * Dependencies of BpfInerfaceMapUpdater, for injection in tests. + */ + @VisibleForTesting + public static class Dependencies { + /** Create BpfMap for updating interface and index mapping. */ + public IBpfMap<U32, InterfaceMapValue> getInterfaceMap() { + try { + return new BpfMap<>(IFACE_INDEX_NAME_MAP_PATH, BpfMap.BPF_F_RDWR, + U32.class, InterfaceMapValue.class); + } catch (ErrnoException e) { + Log.e(TAG, "Cannot create interface map: " + e); + return null; + } + } + + /** Get InterfaceParams for giving interface name. */ + public InterfaceParams getInterfaceParams(String ifaceName) { + return InterfaceParams.getByName(ifaceName); + } + + /** Get INetd binder object. */ + public INetd getINetd(Context ctx) { + return INetd.Stub.asInterface((IBinder) ctx.getSystemService(Context.NETD_SERVICE)); + } + } + + /** + * Start listening interface update event. + * Query current interface names before listening. + */ + public void start() { + mHandler.post(() -> { + if (mBpfMap == null) { + Log.wtf(TAG, "Fail to start: Null bpf map"); + return; + } + + try { + // TODO: use a NetlinkMonitor and listen for RTM_NEWLINK messages instead. + mNetd.registerUnsolicitedEventListener(new InterfaceChangeObserver()); + } catch (RemoteException e) { + Log.wtf(TAG, "Unable to register netd UnsolicitedEventListener, " + e); + } + + final String[] ifaces; + try { + // TODO: use a netlink dump to get the current interface list. + ifaces = mNetd.interfaceGetList(); + } catch (RemoteException | ServiceSpecificException e) { + Log.wtf(TAG, "Unable to query interface names by netd, " + e); + return; + } + + for (String ifaceName : ifaces) { + addInterface(ifaceName); + } + }); + } + + private void addInterface(String ifaceName) { + final InterfaceParams iface = mDeps.getInterfaceParams(ifaceName); + if (iface == null) { + Log.e(TAG, "Unable to get InterfaceParams for " + ifaceName); + return; + } + + try { + mBpfMap.updateEntry(new U32(iface.index), new InterfaceMapValue(ifaceName)); + } catch (ErrnoException e) { + Log.e(TAG, "Unable to update entry for " + ifaceName + ", " + e); + } + } + + private class InterfaceChangeObserver extends BaseNetdUnsolicitedEventListener { + @Override + public void onInterfaceAdded(String ifName) { + mHandler.post(() -> addInterface(ifName)); + } + } +} diff --git a/services/core/java/com/android/server/net/DelayedDiskWrite.java b/packages/ConnectivityT/service/src/com/android/server/net/DelayedDiskWrite.java index 8f09eb7c19ab..35dc4557252c 100644 --- a/services/core/java/com/android/server/net/DelayedDiskWrite.java +++ b/packages/ConnectivityT/service/src/com/android/server/net/DelayedDiskWrite.java @@ -26,21 +26,37 @@ import java.io.DataOutputStream; import java.io.FileOutputStream; import java.io.IOException; +/** + * This class provides APIs to do a delayed data write to a given {@link OutputStream}. + */ public class DelayedDiskWrite { + private static final String TAG = "DelayedDiskWrite"; + private HandlerThread mDiskWriteHandlerThread; private Handler mDiskWriteHandler; /* Tracks multiple writes on the same thread */ private int mWriteSequence = 0; - private final String TAG = "DelayedDiskWrite"; + /** + * Used to do a delayed data write to a given {@link OutputStream}. + */ public interface Writer { - public void onWriteCalled(DataOutputStream out) throws IOException; + /** + * write data to a given {@link OutputStream}. + */ + void onWriteCalled(DataOutputStream out) throws IOException; } + /** + * Do a delayed data write to a given output stream opened from filePath. + */ public void write(final String filePath, final Writer w) { write(filePath, w, true); } + /** + * Do a delayed data write to a given output stream opened from filePath. + */ public void write(final String filePath, final Writer w, final boolean open) { if (TextUtils.isEmpty(filePath)) { throw new IllegalArgumentException("empty file path"); @@ -77,7 +93,7 @@ public class DelayedDiskWrite { if (out != null) { try { out.close(); - } catch (Exception e) {} + } catch (Exception e) { } } // Quit if no more writes sent diff --git a/packages/ConnectivityT/service/src/com/android/server/net/InterfaceMapValue.java b/packages/ConnectivityT/service/src/com/android/server/net/InterfaceMapValue.java new file mode 100644 index 000000000000..061f323447b0 --- /dev/null +++ b/packages/ConnectivityT/service/src/com/android/server/net/InterfaceMapValue.java @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2020 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.net; + +import com.android.net.module.util.Struct; +import com.android.net.module.util.Struct.Field; +import com.android.net.module.util.Struct.Type; + +/** + * The value of bpf interface index map which is used for NetworkStatsService. + */ +public class InterfaceMapValue extends Struct { + @Field(order = 0, type = Type.ByteArray, arraysize = 16) + public final byte[] interfaceName; + + public InterfaceMapValue(String iface) { + final byte[] ifaceArray = iface.getBytes(); + interfaceName = new byte[16]; + // All array bytes after the interface name, if any, must be 0. + System.arraycopy(ifaceArray, 0, interfaceName, 0, ifaceArray.length); + } +} diff --git a/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsFactory.java b/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsFactory.java index bb123a38ebc0..17f3455d20a2 100644 --- a/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsFactory.java +++ b/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsFactory.java @@ -26,10 +26,10 @@ import static com.android.server.NetworkManagementSocketTagger.kernelToTag; import android.annotation.NonNull; import android.annotation.Nullable; -import android.net.INetd; +import android.content.Context; +import android.net.ConnectivityManager; import android.net.NetworkStats; import android.net.UnderlyingNetworkInfo; -import android.os.RemoteException; import android.os.StrictMode; import android.os.SystemClock; @@ -70,7 +70,7 @@ public class NetworkStatsFactory { private final boolean mUseBpfStats; - private final INetd mNetd; + private final Context mContext; /** * Guards persistent data access in this class @@ -158,12 +158,12 @@ public class NetworkStatsFactory { NetworkStats.apply464xlatAdjustments(baseTraffic, stackedTraffic, mStackedIfaces); } - public NetworkStatsFactory(@NonNull INetd netd) { - this(new File("/proc/"), true, netd); + public NetworkStatsFactory(@NonNull Context ctx) { + this(ctx, new File("/proc/"), true); } @VisibleForTesting - public NetworkStatsFactory(File procRoot, boolean useBpfStats, @NonNull INetd netd) { + public NetworkStatsFactory(@NonNull Context ctx, File procRoot, boolean useBpfStats) { mStatsXtIfaceAll = new File(procRoot, "net/xt_qtaguid/iface_stat_all"); mStatsXtIfaceFmt = new File(procRoot, "net/xt_qtaguid/iface_stat_fmt"); mStatsXtUid = new File(procRoot, "net/xt_qtaguid/stats"); @@ -172,7 +172,7 @@ public class NetworkStatsFactory { mPersistSnapshot = new NetworkStats(SystemClock.elapsedRealtime(), -1); mTunAnd464xlatAdjustedStats = new NetworkStats(SystemClock.elapsedRealtime(), -1); } - mNetd = netd; + mContext = ctx; } public NetworkStats readBpfNetworkStatsDev() throws IOException { @@ -295,11 +295,12 @@ public class NetworkStatsFactory { } @GuardedBy("mPersistentDataLock") - private void requestSwapActiveStatsMapLocked() throws RemoteException { - // Ask netd to do a active map stats swap. When the binder call successfully returns, + private void requestSwapActiveStatsMapLocked() { + // Do a active map stats swap. When the binder call successfully returns, // the system server should be able to safely read and clean the inactive map // without race problem. - mNetd.trafficSwapActiveStatsMap(); + final ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class); + cm.swapActiveStatsMap(); } /** @@ -327,7 +328,7 @@ public class NetworkStatsFactory { if (mUseBpfStats) { try { requestSwapActiveStatsMapLocked(); - } catch (RemoteException e) { + } catch (RuntimeException e) { throw new IOException(e); } // Stats are always read from the inactive map, so they must be read after the diff --git a/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsObservers.java b/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsObservers.java index b57a4f920b60..19536247b23b 100644 --- a/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsObservers.java +++ b/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsObservers.java @@ -26,13 +26,12 @@ import android.net.NetworkStatsAccess; import android.net.NetworkStatsCollection; import android.net.NetworkStatsHistory; import android.net.NetworkTemplate; -import android.os.Bundle; +import android.net.netstats.IUsageCallback; import android.os.Handler; import android.os.HandlerThread; import android.os.IBinder; import android.os.Looper; import android.os.Message; -import android.os.Messenger; import android.os.Process; import android.os.RemoteException; import android.util.ArrayMap; @@ -75,10 +74,10 @@ class NetworkStatsObservers { * * @return the normalized request wrapped within {@link RequestInfo}. */ - public DataUsageRequest register(DataUsageRequest inputRequest, Messenger messenger, - IBinder binder, int callingUid, @NetworkStatsAccess.Level int accessLevel) { - DataUsageRequest request = buildRequest(inputRequest); - RequestInfo requestInfo = buildRequestInfo(request, messenger, binder, callingUid, + public DataUsageRequest register(DataUsageRequest inputRequest, IUsageCallback callback, + int callingUid, @NetworkStatsAccess.Level int accessLevel) { + DataUsageRequest request = buildRequest(inputRequest, callingUid); + RequestInfo requestInfo = buildRequestInfo(request, callback, callingUid, accessLevel); if (LOGV) Log.v(TAG, "Registering observer for " + request); @@ -195,10 +194,12 @@ class NetworkStatsObservers { } } - private DataUsageRequest buildRequest(DataUsageRequest request) { - // Cap the minimum threshold to a safe default to avoid too many callbacks - long thresholdInBytes = Math.max(MIN_THRESHOLD_BYTES, request.thresholdInBytes); - if (thresholdInBytes < request.thresholdInBytes) { + private DataUsageRequest buildRequest(DataUsageRequest request, int callingUid) { + // For non-system uid, cap the minimum threshold to a safe default to avoid too + // many callbacks. + long thresholdInBytes = (callingUid == Process.SYSTEM_UID ? request.thresholdInBytes + : Math.max(MIN_THRESHOLD_BYTES, request.thresholdInBytes)); + if (thresholdInBytes > request.thresholdInBytes) { Log.w(TAG, "Threshold was too low for " + request + ". Overriding to a safer default of " + thresholdInBytes + " bytes"); } @@ -206,11 +207,10 @@ class NetworkStatsObservers { request.template, thresholdInBytes); } - private RequestInfo buildRequestInfo(DataUsageRequest request, - Messenger messenger, IBinder binder, int callingUid, - @NetworkStatsAccess.Level int accessLevel) { + private RequestInfo buildRequestInfo(DataUsageRequest request, IUsageCallback callback, + int callingUid, @NetworkStatsAccess.Level int accessLevel) { if (accessLevel <= NetworkStatsAccess.Level.USER) { - return new UserUsageRequestInfo(this, request, messenger, binder, callingUid, + return new UserUsageRequestInfo(this, request, callback, callingUid, accessLevel); } else { // Safety check in case a new access level is added and we forgot to update this @@ -218,7 +218,7 @@ class NetworkStatsObservers { throw new IllegalArgumentException( "accessLevel " + accessLevel + " is less than DEVICESUMMARY."); } - return new NetworkUsageRequestInfo(this, request, messenger, binder, callingUid, + return new NetworkUsageRequestInfo(this, request, callback, callingUid, accessLevel); } } @@ -230,25 +230,23 @@ class NetworkStatsObservers { private abstract static class RequestInfo implements IBinder.DeathRecipient { private final NetworkStatsObservers mStatsObserver; protected final DataUsageRequest mRequest; - private final Messenger mMessenger; - private final IBinder mBinder; + private final IUsageCallback mCallback; protected final int mCallingUid; protected final @NetworkStatsAccess.Level int mAccessLevel; protected NetworkStatsRecorder mRecorder; protected NetworkStatsCollection mCollection; RequestInfo(NetworkStatsObservers statsObserver, DataUsageRequest request, - Messenger messenger, IBinder binder, int callingUid, + IUsageCallback callback, int callingUid, @NetworkStatsAccess.Level int accessLevel) { mStatsObserver = statsObserver; mRequest = request; - mMessenger = messenger; - mBinder = binder; + mCallback = callback; mCallingUid = callingUid; mAccessLevel = accessLevel; try { - mBinder.linkToDeath(this, 0); + mCallback.asBinder().linkToDeath(this, 0); } catch (RemoteException e) { binderDied(); } @@ -257,7 +255,7 @@ class NetworkStatsObservers { @Override public void binderDied() { if (LOGV) { - Log.v(TAG, "RequestInfo binderDied(" + mRequest + ", " + mBinder + ")"); + Log.v(TAG, "RequestInfo binderDied(" + mRequest + ", " + mCallback + ")"); } mStatsObserver.unregister(mRequest, Process.SYSTEM_UID); callCallback(NetworkStatsManager.CALLBACK_RELEASED); @@ -270,9 +268,7 @@ class NetworkStatsObservers { } private void unlinkDeathRecipient() { - if (mBinder != null) { - mBinder.unlinkToDeath(this, 0); - } + mCallback.asBinder().unlinkToDeath(this, 0); } /** @@ -294,17 +290,19 @@ class NetworkStatsObservers { } private void callCallback(int callbackType) { - Bundle bundle = new Bundle(); - bundle.putParcelable(DataUsageRequest.PARCELABLE_KEY, mRequest); - Message msg = Message.obtain(); - msg.what = callbackType; - msg.setData(bundle); try { if (LOGV) { Log.v(TAG, "sending notification " + callbackTypeToName(callbackType) + " for " + mRequest); } - mMessenger.send(msg); + switch (callbackType) { + case NetworkStatsManager.CALLBACK_LIMIT_REACHED: + mCallback.onThresholdReached(mRequest); + break; + case NetworkStatsManager.CALLBACK_RELEASED: + mCallback.onCallbackReleased(mRequest); + break; + } } catch (RemoteException e) { // May occur naturally in the race of binder death. Log.w(TAG, "RemoteException caught trying to send a callback msg for " + mRequest); @@ -334,9 +332,9 @@ class NetworkStatsObservers { private static class NetworkUsageRequestInfo extends RequestInfo { NetworkUsageRequestInfo(NetworkStatsObservers statsObserver, DataUsageRequest request, - Messenger messenger, IBinder binder, int callingUid, + IUsageCallback callback, int callingUid, @NetworkStatsAccess.Level int accessLevel) { - super(statsObserver, request, messenger, binder, callingUid, accessLevel); + super(statsObserver, request, callback, callingUid, accessLevel); } @Override @@ -376,9 +374,9 @@ class NetworkStatsObservers { private static class UserUsageRequestInfo extends RequestInfo { UserUsageRequestInfo(NetworkStatsObservers statsObserver, DataUsageRequest request, - Messenger messenger, IBinder binder, int callingUid, + IUsageCallback callback, int callingUid, @NetworkStatsAccess.Level int accessLevel) { - super(statsObserver, request, messenger, binder, callingUid, accessLevel); + super(statsObserver, request, callback, callingUid, accessLevel); } @Override diff --git a/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsService.java b/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsService.java index a0710f77b4e0..243d62164705 100644 --- a/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsService.java +++ b/packages/ConnectivityT/service/src/com/android/server/net/NetworkStatsService.java @@ -19,12 +19,16 @@ package com.android.server.net; import static android.Manifest.permission.NETWORK_STATS_PROVIDER; import static android.Manifest.permission.READ_NETWORK_USAGE_HISTORY; import static android.Manifest.permission.UPDATE_DEVICE_STATS; +import static android.app.usage.NetworkStatsManager.PREFIX_DEV; +import static android.app.usage.NetworkStatsManager.PREFIX_UID; +import static android.app.usage.NetworkStatsManager.PREFIX_UID_TAG; +import static android.app.usage.NetworkStatsManager.PREFIX_XT; import static android.content.Intent.ACTION_SHUTDOWN; import static android.content.Intent.ACTION_UID_REMOVED; import static android.content.Intent.ACTION_USER_REMOVED; import static android.content.Intent.EXTRA_UID; import static android.content.pm.PackageManager.PERMISSION_GRANTED; -import static android.net.NetworkIdentity.SUBTYPE_COMBINED; +import static android.net.NetworkCapabilities.TRANSPORT_WIFI; import static android.net.NetworkStats.DEFAULT_NETWORK_ALL; import static android.net.NetworkStats.IFACE_ALL; import static android.net.NetworkStats.IFACE_VT; @@ -47,23 +51,6 @@ import static android.net.TrafficStats.MB_IN_BYTES; import static android.net.TrafficStats.UID_TETHERING; import static android.net.TrafficStats.UNSUPPORTED; import static android.os.Trace.TRACE_TAG_NETWORK; -import static android.provider.Settings.Global.NETSTATS_AUGMENT_ENABLED; -import static android.provider.Settings.Global.NETSTATS_COMBINE_SUBTYPE_ENABLED; -import static android.provider.Settings.Global.NETSTATS_DEV_BUCKET_DURATION; -import static android.provider.Settings.Global.NETSTATS_DEV_DELETE_AGE; -import static android.provider.Settings.Global.NETSTATS_DEV_PERSIST_BYTES; -import static android.provider.Settings.Global.NETSTATS_DEV_ROTATE_AGE; -import static android.provider.Settings.Global.NETSTATS_GLOBAL_ALERT_BYTES; -import static android.provider.Settings.Global.NETSTATS_POLL_INTERVAL; -import static android.provider.Settings.Global.NETSTATS_SAMPLE_ENABLED; -import static android.provider.Settings.Global.NETSTATS_UID_BUCKET_DURATION; -import static android.provider.Settings.Global.NETSTATS_UID_DELETE_AGE; -import static android.provider.Settings.Global.NETSTATS_UID_PERSIST_BYTES; -import static android.provider.Settings.Global.NETSTATS_UID_ROTATE_AGE; -import static android.provider.Settings.Global.NETSTATS_UID_TAG_BUCKET_DURATION; -import static android.provider.Settings.Global.NETSTATS_UID_TAG_DELETE_AGE; -import static android.provider.Settings.Global.NETSTATS_UID_TAG_PERSIST_BYTES; -import static android.provider.Settings.Global.NETSTATS_UID_TAG_ROTATE_AGE; import static android.telephony.SubscriptionManager.INVALID_SUBSCRIPTION_ID; import static android.text.format.DateUtils.DAY_IN_MILLIS; import static android.text.format.DateUtils.HOUR_IN_MILLIS; @@ -112,6 +99,7 @@ import android.net.TetheringManager; import android.net.TrafficStats; import android.net.UnderlyingNetworkInfo; import android.net.Uri; +import android.net.netstats.IUsageCallback; import android.net.netstats.provider.INetworkStatsProvider; import android.net.netstats.provider.INetworkStatsProviderCallback; import android.net.netstats.provider.NetworkStatsProvider; @@ -119,12 +107,10 @@ import android.os.Binder; import android.os.DropBoxManager; import android.os.Environment; import android.os.Handler; -import android.os.HandlerExecutor; import android.os.HandlerThread; import android.os.IBinder; import android.os.Looper; import android.os.Message; -import android.os.Messenger; import android.os.PowerManager; import android.os.RemoteException; import android.os.ServiceSpecificException; @@ -217,6 +203,10 @@ public class NetworkStatsService extends INetworkStatsService.Stub { private static final int LOG_TAG_NETSTATS_MOBILE_SAMPLE = 51100; private static final int LOG_TAG_NETSTATS_WIFI_SAMPLE = 51101; + // TODO: Replace the hardcoded string and move it into ConnectivitySettingsManager. + private static final String NETSTATS_COMBINE_SUBTYPE_ENABLED = + "netstats_combine_subtype_enabled"; + private final Context mContext; private final NetworkStatsFactory mStatsFactory; private final AlarmManager mAlarmManager; @@ -243,11 +233,6 @@ public class NetworkStatsService extends INetworkStatsService.Stub { private PendingIntent mPollIntent; - private static final String PREFIX_DEV = "dev"; - private static final String PREFIX_XT = "xt"; - private static final String PREFIX_UID = "uid"; - private static final String PREFIX_UID_TAG = "uid_tag"; - /** * Settings that can be changed externally. */ @@ -257,9 +242,9 @@ public class NetworkStatsService extends INetworkStatsService.Stub { boolean getSampleEnabled(); boolean getAugmentEnabled(); /** - * When enabled, all mobile data is reported under {@link NetworkIdentity#SUBTYPE_COMBINED}. - * When disabled, mobile data is broken down by a granular subtype representative of the - * actual subtype. {@see NetworkTemplate#getCollapsedRatType}. + * When enabled, all mobile data is reported under {@link NetworkTemplate#NETWORK_TYPE_ALL}. + * When disabled, mobile data is broken down by a granular ratType representative of the + * actual ratType. {@see NetworkTemplate#getCollapsedRatType}. * Enabling this decreases the level of detail but saves performance, disk space and * amount of data logged. */ @@ -306,6 +291,9 @@ public class NetworkStatsService extends INetworkStatsService.Stub { /** Set of any ifaces associated with mobile networks since boot. */ private volatile String[] mMobileIfaces = new String[0]; + /** Set of any ifaces associated with wifi networks since boot. */ + private volatile String[] mWifiIfaces = new String[0]; + /** Set of all ifaces currently used by traffic that does not explicitly specify a Network. */ @GuardedBy("mStatsLock") private Network[] mDefaultNetworks = new Network[0]; @@ -369,6 +357,9 @@ public class NetworkStatsService extends INetworkStatsService.Stub { @NonNull private final LocationPermissionChecker mLocationPermissionChecker; + @NonNull + private final BpfInterfaceMapUpdater mInterfaceMapUpdater; + private static @NonNull File getDefaultSystemDir() { return new File(Environment.getDataDirectory(), "system"); } @@ -431,7 +422,7 @@ public class NetworkStatsService extends INetworkStatsService.Stub { final NetworkStatsService service = new NetworkStatsService(context, INetd.Stub.asInterface((IBinder) context.getSystemService(Context.NETD_SERVICE)), alarmManager, wakeLock, getDefaultClock(), - new DefaultNetworkStatsSettings(context), new NetworkStatsFactory(netd), + new DefaultNetworkStatsSettings(), new NetworkStatsFactory(context), new NetworkStatsObservers(), getDefaultSystemDir(), getDefaultBaseDir(), new Dependencies()); @@ -461,11 +452,13 @@ public class NetworkStatsService extends INetworkStatsService.Stub { handlerThread.start(); mHandler = new NetworkStatsHandler(handlerThread.getLooper()); mNetworkStatsSubscriptionsMonitor = deps.makeSubscriptionsMonitor(mContext, - new HandlerExecutor(mHandler), this); + (command) -> mHandler.post(command) , this); mContentResolver = mContext.getContentResolver(); mContentObserver = mDeps.makeContentObserver(mHandler, mSettings, mNetworkStatsSubscriptionsMonitor); mLocationPermissionChecker = mDeps.makeLocationPermissionChecker(mContext); + mInterfaceMapUpdater = mDeps.makeBpfInterfaceMapUpdater(mContext, mHandler); + mInterfaceMapUpdater.start(); } /** @@ -520,6 +513,13 @@ public class NetworkStatsService extends INetworkStatsService.Stub { public LocationPermissionChecker makeLocationPermissionChecker(final Context context) { return new LocationPermissionChecker(context); } + + /** Create BpfInterfaceMapUpdater to update bpf interface map. */ + @NonNull + public BpfInterfaceMapUpdater makeBpfInterfaceMapUpdater( + @NonNull Context ctx, @NonNull Handler handler) { + return new BpfInterfaceMapUpdater(ctx, handler); + } } /** @@ -568,7 +568,7 @@ public class NetworkStatsService extends INetworkStatsService.Stub { // watch for tethering changes final TetheringManager tetheringManager = mContext.getSystemService(TetheringManager.class); tetheringManager.registerTetheringEventCallback( - new HandlerExecutor(mHandler), mTetherListener); + (command) -> mHandler.post(command), mTetherListener); // listen for periodic polling events final IntentFilter pollFilter = new IntentFilter(ACTION_NETWORK_STATS_POLL); @@ -602,13 +602,13 @@ public class NetworkStatsService extends INetworkStatsService.Stub { mSettings.getPollInterval(), pollIntent); mContentResolver.registerContentObserver(Settings.Global - .getUriFor(Settings.Global.NETSTATS_COMBINE_SUBTYPE_ENABLED), + .getUriFor(NETSTATS_COMBINE_SUBTYPE_ENABLED), false /* notifyForDescendants */, mContentObserver); // Post a runnable on handler thread to call onChange(). It's for getting current value of // NETSTATS_COMBINE_SUBTYPE_ENABLED to decide start or stop monitoring RAT type changes. mHandler.post(() -> mContentObserver.onChange(false, Settings.Global - .getUriFor(Settings.Global.NETSTATS_COMBINE_SUBTYPE_ENABLED))); + .getUriFor(NETSTATS_COMBINE_SUBTYPE_ENABLED))); registerGlobalAlert(); } @@ -1000,8 +1000,17 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } // TODO: switch to data layer stats once kernel exports - // for now, read network layer stats and flatten across all ifaces - final NetworkStats networkLayer = readNetworkStatsUidDetail(uid, INTERFACES_ALL, TAG_ALL); + // for now, read network layer stats and flatten across all ifaces. + // This function is used to query NeworkStats for calle's uid. The only caller method + // TrafficStats#getDataLayerSnapshotForUid alrady claim no special permission to query + // its own NetworkStats. + final long ident = Binder.clearCallingIdentity(); + final NetworkStats networkLayer; + try { + networkLayer = readNetworkStatsUidDetail(uid, INTERFACES_ALL, TAG_ALL); + } finally { + Binder.restoreCallingIdentity(ident); + } // splice in operation counts networkLayer.spliceOperationsFrom(mUidOperations); @@ -1020,11 +1029,15 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } @Override - public NetworkStats getDetailedUidStats(String[] requiredIfaces) { + public NetworkStats getUidStatsForTransport(int transport) { enforceAnyPermissionOf(NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK); try { + final String[] relevantIfaces = + transport == TRANSPORT_WIFI ? mWifiIfaces : mMobileIfaces; + // TODO(b/215633405) : mMobileIfaces and mWifiIfaces already contain the stacked + // interfaces, so this is not useful, remove it. final String[] ifacesToQuery = - mStatsFactory.augmentWithStackedInterfaces(requiredIfaces); + mStatsFactory.augmentWithStackedInterfaces(relevantIfaces); return getNetworkStatsUidDetail(ifacesToQuery); } catch (RemoteException e) { Log.wtf(TAG, "Error compiling UID stats", e); @@ -1144,21 +1157,20 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } @Override - public DataUsageRequest registerUsageCallback(String callingPackage, - DataUsageRequest request, Messenger messenger, IBinder binder) { + public DataUsageRequest registerUsageCallback(@NonNull String callingPackage, + @NonNull DataUsageRequest request, @NonNull IUsageCallback callback) { Objects.requireNonNull(callingPackage, "calling package is null"); Objects.requireNonNull(request, "DataUsageRequest is null"); Objects.requireNonNull(request.template, "NetworkTemplate is null"); - Objects.requireNonNull(messenger, "messenger is null"); - Objects.requireNonNull(binder, "binder is null"); + Objects.requireNonNull(callback, "callback is null"); int callingUid = Binder.getCallingUid(); @NetworkStatsAccess.Level int accessLevel = checkAccessLevel(callingPackage); DataUsageRequest normalizedRequest; final long token = Binder.clearCallingIdentity(); try { - normalizedRequest = mStatsObservers.register(request, messenger, binder, - callingUid, accessLevel); + normalizedRequest = mStatsObservers.register( + request, callback, callingUid, accessLevel); } finally { Binder.restoreCallingIdentity(token); } @@ -1383,16 +1395,18 @@ public class NetworkStatsService extends INetworkStatsService.Stub { final boolean combineSubtypeEnabled = mSettings.getCombineSubtypeEnabled(); final ArraySet<String> mobileIfaces = new ArraySet<>(); + final ArraySet<String> wifiIfaces = new ArraySet<>(); for (NetworkStateSnapshot snapshot : snapshots) { final int displayTransport = getDisplayTransport(snapshot.getNetworkCapabilities().getTransportTypes()); final boolean isMobile = (NetworkCapabilities.TRANSPORT_CELLULAR == displayTransport); + final boolean isWifi = (NetworkCapabilities.TRANSPORT_WIFI == displayTransport); final boolean isDefault = CollectionUtils.contains( mDefaultNetworks, snapshot.getNetwork()); - final int subType = combineSubtypeEnabled ? SUBTYPE_COMBINED - : getSubTypeForStateSnapshot(snapshot); + final int ratType = combineSubtypeEnabled ? NetworkTemplate.NETWORK_TYPE_ALL + : getRatTypeForStateSnapshot(snapshot); final NetworkIdentity ident = NetworkIdentity.buildNetworkIdentity(mContext, snapshot, - isDefault, subType); + isDefault, ratType); // Traffic occurring on the base interface is always counted for // both total usage and UID details. @@ -1407,12 +1421,12 @@ public class NetworkStatsService extends INetworkStatsService.Stub { // VT is considered always metered in framework's layer. If VT is not metered // per carrier's policy, modem will report 0 usage for VT calls. if (snapshot.getNetworkCapabilities().hasCapability( - NetworkCapabilities.NET_CAPABILITY_IMS) && !ident.getMetered()) { + NetworkCapabilities.NET_CAPABILITY_IMS) && !ident.isMetered()) { // Copy the identify from IMS one but mark it as metered. NetworkIdentity vtIdent = new NetworkIdentity(ident.getType(), - ident.getSubType(), ident.getSubscriberId(), ident.getNetworkId(), - ident.getRoaming(), true /* metered */, + ident.getRatType(), ident.getSubscriberId(), ident.getWifiNetworkKey(), + ident.isRoaming(), true /* metered */, true /* onDefaultNetwork */, ident.getOemManaged()); final String ifaceVt = IFACE_VT + getSubIdForMobile(snapshot); findOrCreateNetworkIdentitySet(mActiveIfaces, ifaceVt).add(vtIdent); @@ -1422,6 +1436,9 @@ public class NetworkStatsService extends INetworkStatsService.Stub { if (isMobile) { mobileIfaces.add(baseIface); } + if (isWifi) { + wifiIfaces.add(baseIface); + } } // Traffic occurring on stacked interfaces is usually clatd. @@ -1463,6 +1480,9 @@ public class NetworkStatsService extends INetworkStatsService.Stub { if (isMobile) { mobileIfaces.add(iface); } + if (isWifi) { + wifiIfaces.add(iface); + } mStatsFactory.noteStackedIface(iface, baseIface); } @@ -1470,11 +1490,16 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } mMobileIfaces = mobileIfaces.toArray(new String[0]); + mWifiIfaces = wifiIfaces.toArray(new String[0]); // TODO (b/192758557): Remove debug log. if (CollectionUtils.contains(mMobileIfaces, null)) { throw new NullPointerException( "null element in mMobileIfaces: " + Arrays.toString(mMobileIfaces)); } + if (CollectionUtils.contains(mWifiIfaces, null)) { + throw new NullPointerException( + "null element in mWifiIfaces: " + Arrays.toString(mWifiIfaces)); + } } private static int getSubIdForMobile(@NonNull NetworkStateSnapshot state) { @@ -1492,11 +1517,11 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } /** - * For networks with {@code TRANSPORT_CELLULAR}, get subType that was obtained through + * For networks with {@code TRANSPORT_CELLULAR}, get ratType that was obtained through * {@link PhoneStateListener}. Otherwise, return 0 given that other networks with different * transport types do not actually fill this value. */ - private int getSubTypeForStateSnapshot(@NonNull NetworkStateSnapshot state) { + private int getRatTypeForStateSnapshot(@NonNull NetworkStateSnapshot state) { if (!state.getNetworkCapabilities().hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR)) { return 0; } @@ -2243,24 +2268,11 @@ public class NetworkStatsService extends INetworkStatsService.Stub { * {@link android.provider.Settings.Global}. */ private static class DefaultNetworkStatsSettings implements NetworkStatsSettings { - private final ContentResolver mResolver; - - public DefaultNetworkStatsSettings(Context context) { - mResolver = Objects.requireNonNull(context.getContentResolver()); - // TODO: adjust these timings for production builds - } - - private long getGlobalLong(String name, long def) { - return Settings.Global.getLong(mResolver, name, def); - } - private boolean getGlobalBoolean(String name, boolean def) { - final int defInt = def ? 1 : 0; - return Settings.Global.getInt(mResolver, name, defInt) != 0; - } + DefaultNetworkStatsSettings() {} @Override public long getPollInterval() { - return getGlobalLong(NETSTATS_POLL_INTERVAL, 30 * MINUTE_IN_MILLIS); + return 30 * MINUTE_IN_MILLIS; } @Override public long getPollDelay() { @@ -2268,25 +2280,23 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } @Override public long getGlobalAlertBytes(long def) { - return getGlobalLong(NETSTATS_GLOBAL_ALERT_BYTES, def); + return def; } @Override public boolean getSampleEnabled() { - return getGlobalBoolean(NETSTATS_SAMPLE_ENABLED, true); + return true; } @Override public boolean getAugmentEnabled() { - return getGlobalBoolean(NETSTATS_AUGMENT_ENABLED, true); + return true; } @Override public boolean getCombineSubtypeEnabled() { - return getGlobalBoolean(NETSTATS_COMBINE_SUBTYPE_ENABLED, false); + return false; } @Override public Config getDevConfig() { - return new Config(getGlobalLong(NETSTATS_DEV_BUCKET_DURATION, HOUR_IN_MILLIS), - getGlobalLong(NETSTATS_DEV_ROTATE_AGE, 15 * DAY_IN_MILLIS), - getGlobalLong(NETSTATS_DEV_DELETE_AGE, 90 * DAY_IN_MILLIS)); + return new Config(HOUR_IN_MILLIS, 15 * DAY_IN_MILLIS, 90 * DAY_IN_MILLIS); } @Override public Config getXtConfig() { @@ -2294,31 +2304,27 @@ public class NetworkStatsService extends INetworkStatsService.Stub { } @Override public Config getUidConfig() { - return new Config(getGlobalLong(NETSTATS_UID_BUCKET_DURATION, 2 * HOUR_IN_MILLIS), - getGlobalLong(NETSTATS_UID_ROTATE_AGE, 15 * DAY_IN_MILLIS), - getGlobalLong(NETSTATS_UID_DELETE_AGE, 90 * DAY_IN_MILLIS)); + return new Config(2 * HOUR_IN_MILLIS, 15 * DAY_IN_MILLIS, 90 * DAY_IN_MILLIS); } @Override public Config getUidTagConfig() { - return new Config(getGlobalLong(NETSTATS_UID_TAG_BUCKET_DURATION, 2 * HOUR_IN_MILLIS), - getGlobalLong(NETSTATS_UID_TAG_ROTATE_AGE, 5 * DAY_IN_MILLIS), - getGlobalLong(NETSTATS_UID_TAG_DELETE_AGE, 15 * DAY_IN_MILLIS)); + return new Config(2 * HOUR_IN_MILLIS, 5 * DAY_IN_MILLIS, 15 * DAY_IN_MILLIS); } @Override public long getDevPersistBytes(long def) { - return getGlobalLong(NETSTATS_DEV_PERSIST_BYTES, def); + return def; } @Override public long getXtPersistBytes(long def) { - return getDevPersistBytes(def); + return def; } @Override public long getUidPersistBytes(long def) { - return getGlobalLong(NETSTATS_UID_PERSIST_BYTES, def); + return def; } @Override public long getUidTagPersistBytes(long def) { - return getGlobalLong(NETSTATS_UID_TAG_PERSIST_BYTES, def); + return def; } } diff --git a/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java b/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java index a3eb0eccad9d..ce58ff6fc59d 100644 --- a/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java +++ b/packages/ExternalStorageProvider/src/com/android/externalstorage/ExternalStorageProvider.java @@ -236,7 +236,8 @@ public class ExternalStorageProvider extends FileSystemProvider { root.flags |= Root.FLAG_REMOVABLE_USB; } - if (volume.getType() != VolumeInfo.TYPE_EMULATED) { + if (volume.getType() != VolumeInfo.TYPE_EMULATED + && volume.getType() != VolumeInfo.TYPE_STUB) { root.flags |= Root.FLAG_SUPPORTS_EJECT; } diff --git a/packages/SettingsLib/src/com/android/settingslib/NetworkPolicyEditor.java b/packages/SettingsLib/src/com/android/settingslib/NetworkPolicyEditor.java index f5aa652f3194..b4e84dd54654 100644 --- a/packages/SettingsLib/src/com/android/settingslib/NetworkPolicyEditor.java +++ b/packages/SettingsLib/src/com/android/settingslib/NetworkPolicyEditor.java @@ -27,9 +27,7 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.net.NetworkPolicy; import android.net.NetworkPolicyManager; import android.net.NetworkTemplate; -import android.net.wifi.WifiInfo; import android.os.AsyncTask; -import android.text.TextUtils; import android.util.RecurrenceRule; import com.google.android.collect.Lists; @@ -124,7 +122,7 @@ public class NetworkPolicyEditor { if (policy != null) { return policy; } else { - return getPolicy(buildUnquotedNetworkTemplate(template)); + return getPolicy(template); } } @@ -207,21 +205,4 @@ public class NetworkPolicyEditor { policy.clearSnooze(); writeAsync(); } - - /** - * Build a revised {@link NetworkTemplate} that matches the same rule, but - * with an unquoted {@link NetworkTemplate#getNetworkId()}. Used to work - * around legacy bugs. - */ - private static NetworkTemplate buildUnquotedNetworkTemplate(NetworkTemplate template) { - if (template == null) return null; - final String networkId = template.getNetworkId(); - final String strippedNetworkId = WifiInfo.sanitizeSsid(networkId); - if (!TextUtils.equals(strippedNetworkId, networkId)) { - return new NetworkTemplate( - template.getMatchRule(), template.getSubscriberId(), strippedNetworkId); - } else { - return null; - } - } } diff --git a/packages/SettingsLib/src/com/android/settingslib/mobile/OWNERS b/packages/SettingsLib/src/com/android/settingslib/mobile/OWNERS new file mode 100644 index 000000000000..ab9b5dc3ff7a --- /dev/null +++ b/packages/SettingsLib/src/com/android/settingslib/mobile/OWNERS @@ -0,0 +1,4 @@ +# Default reviewers for this and subdirectories. +bonianchen@google.com + +# Emergency approvers in case the above are not available diff --git a/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java b/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java index cff45c6be0e0..30c6645193c0 100644 --- a/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java +++ b/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java @@ -16,7 +16,6 @@ package com.android.settingslib.net; -import static android.net.TrafficStats.MB_IN_BYTES; import static android.telephony.TelephonyManager.SIM_STATE_READY; import static android.text.format.DateUtils.FORMAT_ABBREV_MONTH; import static android.text.format.DateUtils.FORMAT_SHOW_DATE; @@ -49,6 +48,7 @@ public class DataUsageController { private static final StringBuilder PERIOD_BUILDER = new StringBuilder(50); private static final java.util.Formatter PERIOD_FORMATTER = new java.util.Formatter( PERIOD_BUILDER, Locale.getDefault()); + private static final long MB_IN_BYTES = 1024 * 1024; private final Context mContext; private final NetworkPolicyManager mPolicyManager; @@ -237,10 +237,8 @@ public class DataUsageController { final int matchRule = networkTemplate.getMatchRule(); switch (matchRule) { case NetworkTemplate.MATCH_MOBILE: - case NetworkTemplate.MATCH_MOBILE_WILDCARD: return ConnectivityManager.TYPE_MOBILE; case NetworkTemplate.MATCH_WIFI: - case NetworkTemplate.MATCH_WIFI_WILDCARD: return ConnectivityManager.TYPE_WIFI; case NetworkTemplate.MATCH_ETHERNET: return ConnectivityManager.TYPE_ETHERNET; diff --git a/packages/SettingsLib/src/com/android/settingslib/net/DataUsageUtils.java b/packages/SettingsLib/src/com/android/settingslib/net/DataUsageUtils.java index afd44d5bbc90..386a47ae29b0 100644 --- a/packages/SettingsLib/src/com/android/settingslib/net/DataUsageUtils.java +++ b/packages/SettingsLib/src/com/android/settingslib/net/DataUsageUtils.java @@ -63,14 +63,32 @@ public class DataUsageUtils { private static NetworkTemplate getNormalizedMobileTemplate( TelephonyManager telephonyManager, int subId) { final NetworkTemplate mobileTemplate = getMobileTemplateForSubId(telephonyManager, subId); - final String[] mergedSubscriberIds = telephonyManager - .createForSubscriptionId(subId).getMergedImsisFromGroup(); + final Set<String> mergedSubscriberIds = Set.of(telephonyManager + .createForSubscriptionId(subId).getMergedImsisFromGroup()); if (ArrayUtils.isEmpty(mergedSubscriberIds)) { Log.i(TAG, "mergedSubscriberIds is null."); return mobileTemplate; } - return NetworkTemplate.normalize(mobileTemplate, mergedSubscriberIds); + return normalizeMobileTemplate(mobileTemplate, mergedSubscriberIds); + } + + private static NetworkTemplate normalizeMobileTemplate( + NetworkTemplate template, Set<String> mergedSet) { + if (template.getSubscriberIds().isEmpty()) return template; + // The input template should have at most 1 subscriberId. + final String subscriberId = template.getSubscriberIds().iterator().next(); + + if (mergedSet.contains(subscriberId)) { + // Requested template subscriber is part of the merge group; return + // a template that matches all merged subscribers. + return new NetworkTemplate.Builder(template.getMatchRule()) + .setSubscriberIds(mergedSet) + .setWifiNetworkKeys(template.getWifiNetworkKeys()) + .setMeteredness(NetworkStats.METERED_YES).build(); + } + + return template; } private static NetworkTemplate getMobileTemplateForSubId( diff --git a/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataForUidLoader.java b/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataForUidLoader.java index 43c05b8b64d6..504390cd0b63 100644 --- a/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataForUidLoader.java +++ b/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataForUidLoader.java @@ -53,8 +53,9 @@ public class NetworkCycleDataForUidLoader extends long totalUsage = 0L; long totalForeground = 0L; for (int uid : mUids) { - final NetworkStats stats = mNetworkStatsManager.queryDetailsForUid( - mNetworkTemplate, start, end, uid); + final NetworkStats stats = mNetworkStatsManager.queryDetailsForUidTagState( + mNetworkTemplate, start, end, uid, NetworkStats.Bucket.TAG_NONE, + NetworkStats.Bucket.STATE_ALL); final long usage = getTotalUsage(stats); if (usage > 0L) { totalUsage += usage; diff --git a/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataLoader.java b/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataLoader.java index 3e95b01824cc..5e9ac5a59091 100644 --- a/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataLoader.java +++ b/packages/SettingsLib/src/com/android/settingslib/net/NetworkCycleDataLoader.java @@ -16,23 +16,16 @@ package com.android.settingslib.net; -import static android.net.NetworkStatsHistory.FIELD_RX_BYTES; -import static android.net.NetworkStatsHistory.FIELD_TX_BYTES; - +import android.annotation.NonNull; import android.app.usage.NetworkStats; import android.app.usage.NetworkStatsManager; import android.content.Context; -import android.net.INetworkStatsService; -import android.net.INetworkStatsSession; import android.net.NetworkPolicy; import android.net.NetworkPolicyManager; -import android.net.NetworkStatsHistory; import android.net.NetworkTemplate; -import android.net.TrafficStats; -import android.os.RemoteException; -import android.os.ServiceManager; import android.text.format.DateUtils; import android.util.Pair; +import android.util.Range; import androidx.annotation.VisibleForTesting; import androidx.loader.content.AsyncTaskLoader; @@ -52,8 +45,6 @@ public abstract class NetworkCycleDataLoader<D> extends AsyncTaskLoader<D> { protected final NetworkTemplate mNetworkTemplate; private final NetworkPolicy mPolicy; private final ArrayList<Long> mCycles; - @VisibleForTesting - final INetworkStatsService mNetworkStatsService; protected NetworkCycleDataLoader(Builder<?> builder) { super(builder.mContext); @@ -61,8 +52,6 @@ public abstract class NetworkCycleDataLoader<D> extends AsyncTaskLoader<D> { mCycles = builder.mCycles; mNetworkStatsManager = (NetworkStatsManager) builder.mContext.getSystemService(Context.NETWORK_STATS_SERVICE); - mNetworkStatsService = INetworkStatsService.Stub.asInterface( - ServiceManager.getService(Context.NETWORK_STATS_SERVICE)); final NetworkPolicyEditor policyEditor = new NetworkPolicyEditor(NetworkPolicyManager.from(builder.mContext)); policyEditor.read(); @@ -112,23 +101,20 @@ public abstract class NetworkCycleDataLoader<D> extends AsyncTaskLoader<D> { @VisibleForTesting void loadFourWeeksData() { + if (mNetworkTemplate == null) return; + final NetworkStats stats = mNetworkStatsManager.queryDetailsForDevice( + mNetworkTemplate, Long.MIN_VALUE, Long.MAX_VALUE); try { - final INetworkStatsSession networkSession = mNetworkStatsService.openSession(); - final NetworkStatsHistory networkHistory = networkSession.getHistoryForNetwork( - mNetworkTemplate, FIELD_RX_BYTES | FIELD_TX_BYTES); - final long historyStart = networkHistory.getStart(); - final long historyEnd = networkHistory.getEnd(); - - long cycleEnd = historyEnd; - while (cycleEnd > historyStart) { + final Range<Long> historyTimeRange = getTimeRangeOf(stats); + + long cycleEnd = historyTimeRange.getUpper(); + while (cycleEnd > historyTimeRange.getLower()) { final long cycleStart = cycleEnd - (DateUtils.WEEK_IN_MILLIS * 4); recordUsage(cycleStart, cycleEnd); cycleEnd = cycleStart; } - - TrafficStats.closeQuietly(networkSession); - } catch (RemoteException e) { - throw new RuntimeException(e); + } catch (IllegalArgumentException e) { + // Empty history, ignore. } } @@ -169,6 +155,32 @@ public abstract class NetworkCycleDataLoader<D> extends AsyncTaskLoader<D> { return bytes; } + @NonNull + @VisibleForTesting + Range getTimeRangeOf(@NonNull NetworkStats stats) { + long start = Long.MAX_VALUE; + long end = Long.MIN_VALUE; + while (hasNextBucket(stats)) { + final NetworkStats.Bucket bucket = getNextBucket(stats); + start = Math.min(start, bucket.getStartTimeStamp()); + end = Math.max(end, bucket.getEndTimeStamp()); + } + return new Range(start, end); + } + + @VisibleForTesting + boolean hasNextBucket(@NonNull NetworkStats stats) { + return stats.hasNextBucket(); + } + + @NonNull + @VisibleForTesting + NetworkStats.Bucket getNextBucket(@NonNull NetworkStats stats) { + NetworkStats.Bucket bucket = new NetworkStats.Bucket(); + stats.getNextBucket(bucket); + return bucket; + } + @VisibleForTesting(otherwise = VisibleForTesting.NONE) public ArrayList<Long> getCycles() { return mCycles; diff --git a/packages/SettingsLib/src/com/android/settingslib/net/OWNERS b/packages/SettingsLib/src/com/android/settingslib/net/OWNERS new file mode 100644 index 000000000000..ab9b5dc3ff7a --- /dev/null +++ b/packages/SettingsLib/src/com/android/settingslib/net/OWNERS @@ -0,0 +1,4 @@ +# Default reviewers for this and subdirectories. +bonianchen@google.com + +# Emergency approvers in case the above are not available diff --git a/packages/SettingsLib/src/com/android/settingslib/net/UidDetailProvider.java b/packages/SettingsLib/src/com/android/settingslib/net/UidDetailProvider.java index 02326ea85ff6..623eb33f9c0d 100644 --- a/packages/SettingsLib/src/com/android/settingslib/net/UidDetailProvider.java +++ b/packages/SettingsLib/src/com/android/settingslib/net/UidDetailProvider.java @@ -17,6 +17,7 @@ package com.android.settingslib.net; import android.app.AppGlobals; +import android.app.usage.NetworkStats; import android.content.Context; import android.content.pm.ApplicationInfo; import android.content.pm.IPackageManager; @@ -116,13 +117,13 @@ public class UidDetailProvider { detail.label = res.getString(R.string.process_kernel_label); detail.icon = pm.getDefaultActivityIcon(); return detail; - case TrafficStats.UID_REMOVED: + case NetworkStats.Bucket.UID_REMOVED: detail.label = res.getString(UserManager.supportsMultipleUsers() ? R.string.data_usage_uninstalled_apps_users : R.string.data_usage_uninstalled_apps); detail.icon = pm.getDefaultActivityIcon(); return detail; - case TrafficStats.UID_TETHERING: + case NetworkStats.Bucket.UID_TETHERING: final TetheringManager tm = mContext.getSystemService(TetheringManager.class); detail.label = res.getString(Utils.getTetheringLabel(tm)); detail.icon = pm.getDefaultActivityIcon(); diff --git a/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/NetworkCycleDataLoaderTest.java b/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/NetworkCycleDataLoaderTest.java index 74b91510cf3f..c79440e58e17 100644 --- a/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/NetworkCycleDataLoaderTest.java +++ b/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/NetworkCycleDataLoaderTest.java @@ -16,24 +16,24 @@ package com.android.settingslib.net; -import static org.mockito.ArgumentMatchers.anyInt; -import static org.mockito.ArgumentMatchers.nullable; +import static android.app.usage.NetworkStats.Bucket.UID_ALL; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertThrows; import static org.mockito.Mockito.doNothing; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.spy; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; +import android.annotation.NonNull; +import android.app.usage.NetworkStats; import android.app.usage.NetworkStatsManager; import android.content.Context; import android.net.ConnectivityManager; -import android.net.INetworkStatsService; -import android.net.INetworkStatsSession; import android.net.NetworkPolicy; import android.net.NetworkPolicyManager; -import android.net.NetworkStatsHistory; import android.net.NetworkTemplate; -import android.os.RemoteException; import android.text.format.DateUtils; import android.util.Range; @@ -49,6 +49,8 @@ import java.time.ZonedDateTime; import java.util.ArrayList; import java.util.Iterator; import java.util.List; +import java.util.Queue; +import java.util.concurrent.LinkedBlockingQueue; @RunWith(RobolectricTestRunner.class) public class NetworkCycleDataLoaderTest { @@ -63,8 +65,6 @@ public class NetworkCycleDataLoaderTest { private NetworkPolicy mPolicy; @Mock private Iterator<Range<ZonedDateTime>> mIterator; - @Mock - private INetworkStatsService mNetworkStatsService; private NetworkCycleDataTestLoader mLoader; @@ -132,20 +132,24 @@ public class NetworkCycleDataLoaderTest { verify(mLoader).recordUsage(nowInMs, nowInMs); } + private NetworkStats.Bucket makeMockBucket(int uid, long rxBytes, long txBytes, + long start, long end) { + NetworkStats.Bucket ret = mock(NetworkStats.Bucket.class); + when(ret.getUid()).thenReturn(uid); + when(ret.getRxBytes()).thenReturn(rxBytes); + when(ret.getTxBytes()).thenReturn(txBytes); + when(ret.getStartTimeStamp()).thenReturn(start); + when(ret.getEndTimeStamp()).thenReturn(end); + return ret; + } + @Test - public void loadFourWeeksData_shouldRecordUsageForLast4Weeks() throws RemoteException { + public void loadFourWeeksData_shouldRecordUsageForLast4Weeks() { mLoader = spy(new NetworkCycleDataTestLoader(mContext)); - ReflectionHelpers.setField(mLoader, "mNetworkStatsService", mNetworkStatsService); - final INetworkStatsSession networkSession = mock(INetworkStatsSession.class); - when(mNetworkStatsService.openSession()).thenReturn(networkSession); - final NetworkStatsHistory networkHistory = mock(NetworkStatsHistory.class); - when(networkSession.getHistoryForNetwork(nullable(NetworkTemplate.class), anyInt())) - .thenReturn(networkHistory); final long now = System.currentTimeMillis(); final long fourWeeksAgo = now - (DateUtils.WEEK_IN_MILLIS * 4); final long twoDaysAgo = now - (DateUtils.DAY_IN_MILLIS * 2); - when(networkHistory.getStart()).thenReturn(twoDaysAgo); - when(networkHistory.getEnd()).thenReturn(now); + mLoader.addBucket(makeMockBucket(UID_ALL, 123, 456, twoDaysAgo, now)); mLoader.loadFourWeeksData(); @@ -173,10 +177,31 @@ public class NetworkCycleDataLoaderTest { verify(mLoader).recordUsage(thirtyDaysAgo, twentyDaysAgo); } + @Test + public void getTimeRangeOf() { + mLoader = spy(new NetworkCycleDataTestLoader(mContext)); + // If empty, new Range(MAX_VALUE, MIN_VALUE) will be constructed. Hence, the function + // should throw. + assertThrows(IllegalArgumentException.class, + () -> mLoader.getTimeRangeOf(mock(NetworkStats.class))); + + mLoader.addBucket(makeMockBucket(UID_ALL, 123, 456, 0, 10)); + // Feed the function with unused NetworkStats. The actual data injection is + // done by addBucket. + assertEquals(new Range(0L, 10L), mLoader.getTimeRangeOf(mock(NetworkStats.class))); + + mLoader.addBucket(makeMockBucket(UID_ALL, 123, 456, 0, 10)); + mLoader.addBucket(makeMockBucket(UID_ALL, 123, 456, 30, 40)); + mLoader.addBucket(makeMockBucket(UID_ALL, 123, 456, 10, 25)); + assertEquals(new Range(0L, 40L), mLoader.getTimeRangeOf(mock(NetworkStats.class))); + } + public class NetworkCycleDataTestLoader extends NetworkCycleDataLoader<List<NetworkCycleData>> { + private final Queue<NetworkStats.Bucket> mMockedBuckets = new LinkedBlockingQueue<>(); private NetworkCycleDataTestLoader(Context context) { - super(NetworkCycleDataLoader.builder(mContext)); + super(NetworkCycleDataLoader.builder(mContext) + .setNetworkTemplate(mock(NetworkTemplate.class))); mContext = context; } @@ -188,5 +213,19 @@ public class NetworkCycleDataLoaderTest { List<NetworkCycleData> getCycleUsage() { return null; } + + public void addBucket(NetworkStats.Bucket bucket) { + mMockedBuckets.add(bucket); + } + + @Override + public boolean hasNextBucket(@NonNull NetworkStats unused) { + return !mMockedBuckets.isEmpty(); + } + + @Override + public NetworkStats.Bucket getNextBucket(@NonNull NetworkStats unused) { + return mMockedBuckets.remove(); + } } } diff --git a/packages/Shell/AndroidManifest.xml b/packages/Shell/AndroidManifest.xml index 5b9b74a96e1c..5b2e8ae3e7de 100644 --- a/packages/Shell/AndroidManifest.xml +++ b/packages/Shell/AndroidManifest.xml @@ -245,6 +245,7 @@ <uses-permission android:name="android.permission.MANAGE_APP_PREDICTIONS" /> <uses-permission android:name="android.permission.MANAGE_SEARCH_UI" /> <uses-permission android:name="android.permission.MANAGE_SMARTSPACE" /> + <uses-permission android:name="android.permission.MANAGE_WALLPAPER_EFFECTS_GENERATION" /> <uses-permission android:name="android.permission.MANAGE_UI_TRANSLATION" /> <uses-permission android:name="android.permission.NETWORK_SETTINGS" /> <uses-permission android:name="android.permission.CHANGE_WIFI_STATE" /> @@ -503,6 +504,7 @@ <!-- Permission needed for CTS test - WifiManagerTest --> <uses-permission android:name="android.permission.WIFI_ACCESS_COEX_UNSAFE_CHANNELS" /> <uses-permission android:name="android.permission.WIFI_UPDATE_COEX_UNSAFE_CHANNELS" /> + <uses-permission android:name="android.permission.OVERRIDE_WIFI_CONFIG" /> <!-- Permission required for CTS tests to enable/disable rate limiting toasts. --> <uses-permission android:name="android.permission.MANAGE_TOAST_RATE_LIMITING" /> @@ -527,6 +529,10 @@ <!-- Permission required for CTS test - PeopleManagerTest --> <uses-permission android:name="android.permission.READ_PEOPLE_DATA" /> + <!-- Permissions required for CTS test - TrustTestCases --> + <uses-permission android:name="android.permission.PROVIDE_TRUST_AGENT" /> + <uses-permission android:name="android.permission.ACCESS_KEYGUARD_SECURE_STORAGE" /> + <!-- Permission required for CTS test - CtsGameManagerTestCases --> <uses-permission android:name="android.permission.MANAGE_GAME_MODE" /> diff --git a/packages/SystemUI/OWNERS b/packages/SystemUI/OWNERS index e1da74466b55..8323e326dea1 100644 --- a/packages/SystemUI/OWNERS +++ b/packages/SystemUI/OWNERS @@ -11,8 +11,10 @@ asc@google.com awickham@google.com beverlyt@google.com brockman@google.com +brzezinski@google.com brycelee@google.com ccassidy@google.com +chrisgollner@google.com cinek@google.com cwren@google.com dupin@google.com @@ -43,6 +45,8 @@ mpietal@google.com mrcasey@google.com mrenouf@google.com nesciosquid@google.com +nickchameyev@google.com +nicomazz@google.com ogunwale@google.com peanutbutter@google.com pinyaoting@google.com @@ -67,6 +71,7 @@ winsonc@google.com yurilin@google.com xuqiu@google.com zakcohen@google.com +jernej@google.com #Android Auto hseog@google.com diff --git a/services/Android.bp b/services/Android.bp index 8fb9ae86a15f..8947393849c1 100644 --- a/services/Android.bp +++ b/services/Android.bp @@ -176,6 +176,10 @@ cc_library_shared { name: "libandroid_servers", defaults: ["libservices.core-libs"], whole_static_libs: ["libservices.core"], + required: [ + // TODO: remove after NetworkStatsService is moved to the mainline module. + "libcom_android_net_module_util_jni", + ], } platform_compat_config { diff --git a/services/core/Android.bp b/services/core/Android.bp index 960f7ca63b1d..9d190087e300 100644 --- a/services/core/Android.bp +++ b/services/core/Android.bp @@ -166,6 +166,9 @@ java_library_static { "overlayable_policy_aidl-java", "SurfaceFlingerProperties", "com.android.sysprop.watchdog", + // This is used for services.connectivity-tiramisu-sources. + // TODO: delete when NetworkStatsService is moved to the mainline module. + "net-utils-device-common-bpf", ], javac_shard_size: 50, } diff --git a/services/core/java/android/app/usage/OWNERS b/services/core/java/android/app/usage/OWNERS new file mode 100644 index 000000000000..3a555143b11d --- /dev/null +++ b/services/core/java/android/app/usage/OWNERS @@ -0,0 +1 @@ +include platform/frameworks/base:/core/java/android/app/usage/OWNERS diff --git a/services/core/java/com/android/server/NetworkManagementService.java b/services/core/java/com/android/server/NetworkManagementService.java index 39516802e93b..8551d887e80c 100644 --- a/services/core/java/com/android/server/NetworkManagementService.java +++ b/services/core/java/com/android/server/NetworkManagementService.java @@ -20,12 +20,12 @@ import static android.Manifest.permission.CONNECTIVITY_INTERNAL; import static android.Manifest.permission.NETWORK_SETTINGS; import static android.Manifest.permission.OBSERVE_NETWORK_POLICY; import static android.Manifest.permission.SHUTDOWN; +import static android.net.ConnectivityManager.FIREWALL_CHAIN_DOZABLE; +import static android.net.ConnectivityManager.FIREWALL_CHAIN_POWERSAVE; +import static android.net.ConnectivityManager.FIREWALL_CHAIN_RESTRICTED; +import static android.net.ConnectivityManager.FIREWALL_CHAIN_STANDBY; import static android.net.INetd.FIREWALL_ALLOWLIST; -import static android.net.INetd.FIREWALL_CHAIN_DOZABLE; import static android.net.INetd.FIREWALL_CHAIN_NONE; -import static android.net.INetd.FIREWALL_CHAIN_POWERSAVE; -import static android.net.INetd.FIREWALL_CHAIN_RESTRICTED; -import static android.net.INetd.FIREWALL_CHAIN_STANDBY; import static android.net.INetd.FIREWALL_DENYLIST; import static android.net.INetd.FIREWALL_RULE_ALLOW; import static android.net.INetd.FIREWALL_RULE_DENY; @@ -44,6 +44,7 @@ import static com.android.net.module.util.NetworkStatsUtils.LIMIT_GLOBAL_ALERT; import android.annotation.NonNull; import android.app.ActivityManager; import android.content.Context; +import android.net.ConnectivityManager; import android.net.INetd; import android.net.INetdUnsolicitedEventListener; import android.net.INetworkManagementEventObserver; @@ -1158,19 +1159,12 @@ public class NetworkManagementService extends INetworkManagementService.Stub { } Trace.traceBegin(Trace.TRACE_TAG_NETWORK, "inetd bandwidth"); + final ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class); try { if (allowlist) { - if (enable) { - mNetdService.bandwidthAddNiceApp(uid); - } else { - mNetdService.bandwidthRemoveNiceApp(uid); - } + cm.updateMeteredNetworkAllowList(uid, enable); } else { - if (enable) { - mNetdService.bandwidthAddNaughtyApp(uid); - } else { - mNetdService.bandwidthRemoveNaughtyApp(uid); - } + cm.updateMeteredNetworkDenyList(uid, enable); } synchronized (mRulesLock) { if (enable) { @@ -1179,7 +1173,7 @@ public class NetworkManagementService extends INetworkManagementService.Stub { quotaList.delete(uid); } } - } catch (RemoteException | ServiceSpecificException e) { + } catch (RuntimeException e) { throw new IllegalStateException(e); } finally { Trace.traceEnd(Trace.TRACE_TAG_NETWORK); @@ -1464,9 +1458,10 @@ public class NetworkManagementService extends INetworkManagementService.Stub { throw new IllegalArgumentException("Bad child chain: " + chainName); } + final ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class); try { - mNetdService.firewallEnableChildChain(chain, enable); - } catch (RemoteException | ServiceSpecificException e) { + cm.setFirewallChainEnabled(chain, enable); + } catch (RuntimeException e) { throw new IllegalStateException(e); } @@ -1538,25 +1533,10 @@ public class NetworkManagementService extends INetworkManagementService.Stub { updateFirewallUidRuleLocked(chain, uid, FIREWALL_RULE_DEFAULT); } } + final ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class); try { - switch (chain) { - case FIREWALL_CHAIN_DOZABLE: - mNetdService.firewallReplaceUidChain("fw_dozable", true, uids); - break; - case FIREWALL_CHAIN_STANDBY: - mNetdService.firewallReplaceUidChain("fw_standby", false, uids); - break; - case FIREWALL_CHAIN_POWERSAVE: - mNetdService.firewallReplaceUidChain("fw_powersave", true, uids); - break; - case FIREWALL_CHAIN_RESTRICTED: - mNetdService.firewallReplaceUidChain("fw_restricted", true, uids); - break; - case FIREWALL_CHAIN_NONE: - default: - Slog.d(TAG, "setFirewallUidRules() called on invalid chain: " + chain); - } - } catch (RemoteException e) { + cm.replaceFirewallChain(chain, uids); + } catch (RuntimeException e) { Slog.w(TAG, "Error flushing firewall chain " + chain, e); } } @@ -1572,10 +1552,10 @@ public class NetworkManagementService extends INetworkManagementService.Stub { private void setFirewallUidRuleLocked(int chain, int uid, int rule) { if (updateFirewallUidRuleLocked(chain, uid, rule)) { - final int ruleType = getFirewallRuleType(chain, rule); + final ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class); try { - mNetdService.firewallSetUidRule(chain, uid, ruleType); - } catch (RemoteException | ServiceSpecificException e) { + cm.updateFirewallRule(chain, uid, isFirewallRuleAllow(chain, rule)); + } catch (RuntimeException e) { throw new IllegalStateException(e); } } @@ -1645,12 +1625,12 @@ public class NetworkManagementService extends INetworkManagementService.Stub { } } - private int getFirewallRuleType(int chain, int rule) { + // There are only two type of firewall rule: FIREWALL_RULE_ALLOW or FIREWALL_RULE_DENY. + private boolean isFirewallRuleAllow(int chain, int rule) { if (rule == NetworkPolicyManager.FIREWALL_RULE_DEFAULT) { - return getFirewallType(chain) == FIREWALL_ALLOWLIST - ? INetd.FIREWALL_RULE_DENY : INetd.FIREWALL_RULE_ALLOW; + return getFirewallType(chain) == FIREWALL_DENYLIST; } - return rule; + return rule == INetd.FIREWALL_RULE_ALLOW; } private void enforceSystemUid() { diff --git a/services/core/java/com/android/server/StorageManagerService.java b/services/core/java/com/android/server/StorageManagerService.java index 53c8635c4e0a..9546496fd8e8 100644 --- a/services/core/java/com/android/server/StorageManagerService.java +++ b/services/core/java/com/android/server/StorageManagerService.java @@ -3620,8 +3620,12 @@ class StorageManagerService extends IStorageManager.Stub mInstaller.tryMountDataMirror(volumeUuid); } } - } catch (Exception e) { + } catch (RemoteException | Installer.InstallerException e) { Slog.wtf(TAG, e); + // Make sure to re-throw this exception; we must not ignore failure + // to prepare the user storage as it could indicate that encryption + // wasn't successfully set up. + throw new RuntimeException(e); } } diff --git a/services/core/java/com/android/server/clipboard/OWNERS b/services/core/java/com/android/server/clipboard/OWNERS index 5449df908051..0d5dbf9acac3 100644 --- a/services/core/java/com/android/server/clipboard/OWNERS +++ b/services/core/java/com/android/server/clipboard/OWNERS @@ -1 +1,3 @@ per-file EmulatorClipboardMonitor.java = bohu@google.com,lfy@google.com,rkir@google.com + +olilan@google.com diff --git a/services/core/java/com/android/server/connectivity/MultipathPolicyTracker.java b/services/core/java/com/android/server/connectivity/MultipathPolicyTracker.java index fce673765020..603f20633cfb 100644 --- a/services/core/java/com/android/server/connectivity/MultipathPolicyTracker.java +++ b/services/core/java/com/android/server/connectivity/MultipathPolicyTracker.java @@ -18,14 +18,12 @@ package com.android.server.connectivity; import static android.net.ConnectivityManager.MULTIPATH_PREFERENCE_HANDOVER; import static android.net.ConnectivityManager.MULTIPATH_PREFERENCE_RELIABILITY; -import static android.net.ConnectivityManager.TYPE_MOBILE; import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET; import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_METERED; import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING; import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR; import static android.net.NetworkPolicy.LIMIT_DISABLED; import static android.net.NetworkPolicy.WARNING_DISABLED; -import static android.net.NetworkTemplate.OEM_MANAGED_ALL; import static android.provider.Settings.Global.NETWORK_DEFAULT_DAILY_MULTIPATH_QUOTA_BYTES; import static android.telephony.SubscriptionManager.INVALID_SUBSCRIPTION_ID; @@ -95,6 +93,7 @@ public class MultipathPolicyTracker { private static String TAG = MultipathPolicyTracker.class.getSimpleName(); private static final boolean DBG = false; + private static final long MIN_THRESHOLD_BYTES = 2 * 1_048_576L; // 2MiB // This context is for the current user. private final Context mContext; @@ -279,15 +278,11 @@ public class MultipathPolicyTracker { } private NetworkIdentity getTemplateMatchingNetworkIdentity(NetworkCapabilities nc) { - return new NetworkIdentity( - ConnectivityManager.TYPE_MOBILE, - 0 /* subType, unused for template matching */, - subscriberId, - null /* networkId, unused for matching mobile networks */, - !nc.hasCapability(NET_CAPABILITY_NOT_ROAMING), - !nc.hasCapability(NET_CAPABILITY_NOT_METERED), - false /* defaultNetwork, templates should have DEFAULT_NETWORK_ALL */, - OEM_MANAGED_ALL); + return new NetworkIdentity.Builder().setType(ConnectivityManager.TYPE_MOBILE) + .setSubscriberId(subscriberId) + .setRoaming(!nc.hasCapability(NET_CAPABILITY_NOT_ROAMING)) + .setMetered(!nc.hasCapability(NET_CAPABILITY_NOT_METERED)) + .build(); } private long getRemainingDailyBudget(long limitBytes, @@ -376,7 +371,7 @@ public class MultipathPolicyTracker { // This will only be called if the total quota for the day changed, not if usage changed // since last time, so even if this is called very often the budget will not snap to 0 // as soon as there are less than 2MB left for today. - if (budget > NetworkStatsManager.MIN_THRESHOLD_BYTES) { + if (budget > MIN_THRESHOLD_BYTES) { if (DBG) { Log.d(TAG, "Setting callback for " + budget + " bytes on network " + network); } @@ -409,8 +404,8 @@ public class MultipathPolicyTracker { private void registerUsageCallback(long budget) { maybeUnregisterUsageCallback(); - mStatsManager.registerUsageCallback(mNetworkTemplate, TYPE_MOBILE, budget, - mUsageCallback, mHandler); + mStatsManager.registerUsageCallback(mNetworkTemplate, budget, + (command) -> mHandler.post(command), mUsageCallback); mMultipathBudget = budget; } diff --git a/services/core/java/com/android/server/media/BluetoothRouteProvider.java b/services/core/java/com/android/server/media/BluetoothRouteProvider.java index ffc1aed4c672..91de9e559e13 100644 --- a/services/core/java/com/android/server/media/BluetoothRouteProvider.java +++ b/services/core/java/com/android/server/media/BluetoothRouteProvider.java @@ -344,10 +344,19 @@ class BluetoothRouteProvider { } private void addActiveRoute(BluetoothRouteInfo btRoute) { + if (btRoute == null) { + if (DEBUG) { + Log.d(TAG, " btRoute is null"); + } + return; + } if (DEBUG) { Log.d(TAG, "Adding active route: " + btRoute.route); } - if (btRoute == null || mActiveRoutes.contains(btRoute)) { + if (mActiveRoutes.contains(btRoute)) { + if (DEBUG) { + Log.d(TAG, " btRoute is already added."); + } return; } setRouteConnectionState(btRoute, STATE_CONNECTED); diff --git a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java index 8902d0d2cac4..c05138f8eae1 100644 --- a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java +++ b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java @@ -24,7 +24,6 @@ import static android.Manifest.permission.MANAGE_SUBSCRIPTION_PLANS; import static android.Manifest.permission.NETWORK_SETTINGS; import static android.Manifest.permission.NETWORK_STACK; import static android.Manifest.permission.OBSERVE_NETWORK_POLICY; -import static android.Manifest.permission.READ_NETWORK_USAGE_HISTORY; import static android.Manifest.permission.READ_PHONE_STATE; import static android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE; import static android.app.PendingIntent.FLAG_IMMUTABLE; @@ -63,7 +62,6 @@ import static android.net.INetd.FIREWALL_RULE_DENY; import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_METERED; import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_ROAMING; import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR; -import static android.net.NetworkIdentity.OEM_NONE; import static android.net.NetworkPolicy.LIMIT_DISABLED; import static android.net.NetworkPolicy.SNOOZE_NEVER; import static android.net.NetworkPolicy.WARNING_DISABLED; @@ -102,7 +100,6 @@ import static android.net.NetworkTemplate.MATCH_MOBILE; import static android.net.NetworkTemplate.MATCH_WIFI; import static android.net.NetworkTemplate.buildTemplateCarrierMetered; import static android.net.NetworkTemplate.buildTemplateMobileAll; -import static android.net.TrafficStats.MB_IN_BYTES; import static android.net.netstats.provider.NetworkStatsProvider.QUOTA_UNLIMITED; import static android.os.Trace.TRACE_TAG_NETWORK; import static android.provider.Settings.Global.NETPOLICY_OVERRIDE_ENABLED; @@ -131,7 +128,6 @@ import static com.android.internal.util.XmlUtils.writeIntAttribute; import static com.android.internal.util.XmlUtils.writeLongAttribute; import static com.android.internal.util.XmlUtils.writeStringAttribute; import static com.android.net.module.util.NetworkStatsUtils.LIMIT_GLOBAL_ALERT; -import static com.android.server.net.NetworkStatsService.ACTION_NETWORK_STATS_UPDATED; import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; import static org.xmlpull.v1.XmlPullParser.END_TAG; @@ -185,7 +181,6 @@ import android.net.NetworkStack; import android.net.NetworkStateSnapshot; import android.net.NetworkTemplate; import android.net.TelephonyNetworkSpecifier; -import android.net.TrafficStats; import android.net.wifi.WifiConfiguration; import android.net.wifi.WifiManager; import android.os.BestClock; @@ -1013,10 +1008,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { userFilter.addAction(ACTION_USER_REMOVED); mContext.registerReceiver(mUserReceiver, userFilter, null, mHandler); - // listen for stats update events - final IntentFilter statsFilter = new IntentFilter(ACTION_NETWORK_STATS_UPDATED); - mContext.registerReceiver( - mStatsReceiver, statsFilter, READ_NETWORK_USAGE_HISTORY, mHandler); + // listen for stats updated callbacks for interested network types. + mNetworkStats.registerUsageCallback(new NetworkTemplate.Builder(MATCH_MOBILE).build(), + 0 /* thresholdBytes */, new HandlerExecutor(mHandler), mStatsCallback); + mNetworkStats.registerUsageCallback(new NetworkTemplate.Builder(MATCH_WIFI).build(), + 0 /* thresholdBytes */, new HandlerExecutor(mHandler), mStatsCallback); // listen for restrict background changes from notifications final IntentFilter allowFilter = new IntentFilter(ACTION_ALLOW_BACKGROUND); @@ -1221,19 +1217,16 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { }; /** - * Receiver that watches for {@link NetworkStatsManager} updates, which we - * use to check against {@link NetworkPolicy#warningBytes}. + * Listener that watches for {@link NetworkStatsManager} updates, which + * NetworkPolicyManagerService uses to check against {@link NetworkPolicy#warningBytes}. */ - private final NetworkStatsBroadcastReceiver mStatsReceiver = - new NetworkStatsBroadcastReceiver(); - private class NetworkStatsBroadcastReceiver extends BroadcastReceiver { - private boolean mIsAnyIntentReceived = false; - @Override - public void onReceive(Context context, Intent intent) { - // on background handler thread, and verified - // READ_NETWORK_USAGE_HISTORY permission above. + private final StatsCallback mStatsCallback = new StatsCallback(); + private class StatsCallback extends NetworkStatsManager.UsageCallback { + private boolean mIsAnyCallbackReceived = false; - mIsAnyIntentReceived = true; + @Override + public void onThresholdReached(int networkType, String subscriberId) { + mIsAnyCallbackReceived = true; synchronized (mNetworkPoliciesSecondLock) { updateNetworkRulesNL(); @@ -1243,11 +1236,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { } /** - * Return whether any {@code ACTION_NETWORK_STATS_UPDATED} intent is received. + * Return whether any callback is received. * Used to determine if NetworkStatsService is ready. */ - public boolean isAnyIntentReceived() { - return mIsAnyIntentReceived; + public boolean isAnyCallbackReceived() { + return mIsAnyCallbackReceived; } }; @@ -1474,7 +1467,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { // Skip if not ready. NetworkStatsService will block public API calls until it is // ready. To prevent NPMS be blocked on that, skip and fail fast instead. - if (!mStatsReceiver.isAnyIntentReceived()) return null; + if (!mStatsCallback.isAnyCallbackReceived()) return null; final List<NetworkStats.Bucket> stats = mDeps.getNetworkUidBytes(template, start, end); for (final NetworkStats.Bucket entry : stats) { @@ -1518,13 +1511,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { for (int i = 0; i < mSubIdToSubscriberId.size(); i++) { final int subId = mSubIdToSubscriberId.keyAt(i); final String subscriberId = mSubIdToSubscriberId.valueAt(i); - final NetworkIdentity probeIdent = new NetworkIdentity(TYPE_MOBILE, - TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false, true, - true, OEM_NONE); - /* While OEM_NONE indicates "any non OEM managed network", OEM_NONE is meant to be a - * placeholder value here. The probeIdent is matched against a NetworkTemplate which - * should have its OEM managed value set to OEM_MANAGED_ALL, which will cause the - * template to match probeIdent without regard to OEM managed status. */ + final NetworkIdentity probeIdent = new NetworkIdentity.Builder() + .setType(TYPE_MOBILE) + .setSubscriberId(subscriberId) + .setMetered(true) + .setDefaultNetwork(true).build(); if (template.matches(probeIdent)) { return subId; } @@ -1757,9 +1748,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { // find and update the carrier NetworkPolicy for this subscriber id boolean policyUpdated = false; - final NetworkIdentity probeIdent = new NetworkIdentity(TYPE_MOBILE, - TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false, true, true, - OEM_NONE); + final NetworkIdentity probeIdent = new NetworkIdentity.Builder() + .setType(TYPE_MOBILE) + .setSubscriberId(subscriberId) + .setMetered(true) + .setDefaultNetwork(true).build(); for (int i = mNetworkPolicy.size() - 1; i >= 0; i--) { final NetworkTemplate template = mNetworkPolicy.keyAt(i); if (template.matches(probeIdent)) { @@ -1987,10 +1980,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { for (int i = 0; i < mSubIdToSubscriberId.size(); i++) { final int subId = mSubIdToSubscriberId.keyAt(i); final String subscriberId = mSubIdToSubscriberId.valueAt(i); - - final NetworkIdentity probeIdent = new NetworkIdentity(TYPE_MOBILE, - TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false, true, - true, OEM_NONE); + final NetworkIdentity probeIdent = new NetworkIdentity.Builder() + .setType(TYPE_MOBILE) + .setSubscriberId(subscriberId) + .setMetered(true) + .setDefaultNetwork(true).build(); // Template is matched when subscriber id matches. if (template.matches(probeIdent)) { matchingSubIds.add(subId); @@ -2094,11 +2088,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { for (final NetworkStateSnapshot snapshot : snapshots) { mNetIdToSubId.put(snapshot.getNetwork().getNetId(), parseSubId(snapshot)); - // Policies matched by NPMS only match by subscriber ID or by network ID. Thus subtype - // in the object created here is never used and its value doesn't matter, so use - // NETWORK_TYPE_UNKNOWN. - final NetworkIdentity ident = NetworkIdentity.buildNetworkIdentity(mContext, snapshot, - true, TelephonyManager.NETWORK_TYPE_UNKNOWN /* subType */); + // Policies matched by NPMS only match by subscriber ID or by network ID. + final NetworkIdentity ident = new NetworkIdentity.Builder() + .setNetworkStateSnapshot(snapshot).setDefaultNetwork(true).build(); identified.put(snapshot, ident); } @@ -2295,9 +2287,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { @GuardedBy("mNetworkPoliciesSecondLock") private boolean ensureActiveCarrierPolicyAL(int subId, String subscriberId) { // Poke around to see if we already have a policy - final NetworkIdentity probeIdent = new NetworkIdentity(TYPE_MOBILE, - TelephonyManager.NETWORK_TYPE_UNKNOWN, subscriberId, null, false, true, true, - OEM_NONE); + final NetworkIdentity probeIdent = new NetworkIdentity.Builder() + .setType(TYPE_MOBILE) + .setSubscriberId(subscriberId) + .setMetered(true) + .setDefaultNetwork(true).build(); for (int i = mNetworkPolicy.size() - 1; i >= 0; i--) { final NetworkTemplate template = mNetworkPolicy.keyAt(i); if (template.matches(probeIdent)) { @@ -2323,7 +2317,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { if (dataWarningConfig == WARNING_DISABLED) { return WARNING_DISABLED; } else { - return dataWarningConfig * MB_IN_BYTES; + return DataUnit.MEBIBYTES.toBytes(dataWarningConfig); } } @@ -2707,7 +2701,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { final List<WifiConfiguration> configs = wm.getConfiguredNetworks(); for (int i = 0; i < configs.size(); ++i) { final WifiConfiguration config = configs.get(i); - for (String key : config.getAllPersistableNetworkKeys()) { + for (String key : config.getAllNetworkKeys()) { final Boolean metered = wifiNetworkKeys.get(key); if (metered != null) { Slog.d(TAG, "Found network " + key + "; upgrading metered hint"); @@ -3492,9 +3486,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2007-03-14T00:00:00.000Z")) .setTitle("G-Mobile") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_BILLED) - .setDataUsage(1 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(1), ZonedDateTime.now().minusHours(36).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder @@ -3502,15 +3496,15 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { .setTitle("G-Mobile Happy") .setDataLimit(SubscriptionPlan.BYTES_UNLIMITED, SubscriptionPlan.LIMIT_BEHAVIOR_BILLED) - .setDataUsage(5 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(5), ZonedDateTime.now().minusHours(36).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2017-03-14T00:00:00.000Z")) .setTitle("G-Mobile, Charged after limit") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_BILLED) - .setDataUsage(5 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(5), ZonedDateTime.now().minusHours(36).toInstant().toEpochMilli()) .build()); } else if ("month_soft".equals(fake)) { @@ -3519,25 +3513,25 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { .setTitle("G-Mobile is the carriers name who this plan belongs to") .setSummary("Crazy unlimited bandwidth plan with incredibly long title " + "that should be cut off to prevent UI from looking terrible") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(1 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(1), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2017-03-14T00:00:00.000Z")) .setTitle("G-Mobile, Throttled after limit") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(5 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(5), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2017-03-14T00:00:00.000Z")) .setTitle("G-Mobile, No data connection after limit") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED) - .setDataUsage(5 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(5), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); @@ -3545,25 +3539,25 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2007-03-14T00:00:00.000Z")) .setTitle("G-Mobile is the carriers name who this plan belongs to") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(6 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(6), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2017-03-14T00:00:00.000Z")) .setTitle("G-Mobile, Throttled after limit") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(5 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(5), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder .createRecurringMonthly(ZonedDateTime.parse("2017-03-14T00:00:00.000Z")) .setTitle("G-Mobile, No data connection after limit") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED) - .setDataUsage(5 * TrafficStats.GB_IN_BYTES, + .setDataUsage(DataUnit.GIBIBYTES.toBytes(5), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); @@ -3577,9 +3571,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { .createNonrecurring(ZonedDateTime.now().minusDays(20), ZonedDateTime.now().plusDays(10)) .setTitle("G-Mobile") - .setDataLimit(512 * TrafficStats.MB_IN_BYTES, + .setDataLimit(DataUnit.MEBIBYTES.toBytes(512), SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED) - .setDataUsage(100 * TrafficStats.MB_IN_BYTES, + .setDataUsage(DataUnit.MEBIBYTES.toBytes(100), ZonedDateTime.now().minusHours(3).toInstant().toEpochMilli()) .build()); } else if ("prepaid_crazy".equals(fake)) { @@ -3587,9 +3581,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { .createNonrecurring(ZonedDateTime.now().minusDays(20), ZonedDateTime.now().plusDays(10)) .setTitle("G-Mobile Anytime") - .setDataLimit(512 * TrafficStats.MB_IN_BYTES, + .setDataLimit(DataUnit.MEBIBYTES.toBytes(512), SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED) - .setDataUsage(100 * TrafficStats.MB_IN_BYTES, + .setDataUsage(DataUnit.MEBIBYTES.toBytes(100), ZonedDateTime.now().minusHours(3).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder @@ -3597,9 +3591,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { ZonedDateTime.now().plusDays(20)) .setTitle("G-Mobile Nickel Nights") .setSummary("5¢/GB between 1-5AM") - .setDataLimit(5 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(5), SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(15 * TrafficStats.MB_IN_BYTES, + .setDataUsage(DataUnit.MEBIBYTES.toBytes(15), ZonedDateTime.now().minusHours(30).toInstant().toEpochMilli()) .build()); plans.add(SubscriptionPlan.Builder @@ -3607,9 +3601,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { ZonedDateTime.now().plusDays(20)) .setTitle("G-Mobile Bonus 3G") .setSummary("Unlimited 3G data") - .setDataLimit(1 * TrafficStats.GB_IN_BYTES, + .setDataLimit(DataUnit.GIBIBYTES.toBytes(1), SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(300 * TrafficStats.MB_IN_BYTES, + .setDataUsage(DataUnit.MEBIBYTES.toBytes(300), ZonedDateTime.now().minusHours(1).toInstant().toEpochMilli()) .build()); } else if ("unlimited".equals(fake)) { @@ -3619,7 +3613,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { .setTitle("G-Mobile Awesome") .setDataLimit(SubscriptionPlan.BYTES_UNLIMITED, SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED) - .setDataUsage(50 * TrafficStats.MB_IN_BYTES, + .setDataUsage(DataUnit.MEBIBYTES.toBytes(50), ZonedDateTime.now().minusHours(3).toInstant().toEpochMilli()) .build()); } @@ -5470,7 +5464,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub { private long getTotalBytes(NetworkTemplate template, long start, long end) { // Skip if not ready. NetworkStatsService will block public API calls until it is // ready. To prevent NPMS be blocked on that, skip and fail fast instead. - if (!mStatsReceiver.isAnyIntentReceived()) return 0; + if (!mStatsCallback.isAnyCallbackReceived()) return 0; return mDeps.getNetworkTotalBytes(template, start, end); } diff --git a/services/core/java/com/android/server/pm/UserDataPreparer.java b/services/core/java/com/android/server/pm/UserDataPreparer.java index 045a295da965..504769064808 100644 --- a/services/core/java/com/android/server/pm/UserDataPreparer.java +++ b/services/core/java/com/android/server/pm/UserDataPreparer.java @@ -22,6 +22,7 @@ import android.content.Context; import android.content.pm.UserInfo; import android.os.Environment; import android.os.FileUtils; +import android.os.RecoverySystem; import android.os.storage.StorageManager; import android.os.storage.VolumeInfo; import android.os.SystemProperties; @@ -115,6 +116,13 @@ class UserDataPreparer { // Try one last time; if we fail again we're really in trouble prepareUserDataLI(volumeUuid, userId, userSerial, flags | StorageManager.FLAG_STORAGE_DE, false); + } else { + try { + Log.e(TAG, "prepareUserData failed", e); + RecoverySystem.rebootPromptAndWipeUserData(mContext, "prepareUserData failed"); + } catch (IOException e2) { + throw new RuntimeException("error rebooting into recovery", e2); + } } } } diff --git a/services/core/java/com/android/server/stats/pull/StatsPullAtomService.java b/services/core/java/com/android/server/stats/pull/StatsPullAtomService.java index bbd4d058dfaf..758877b3f266 100644 --- a/services/core/java/com/android/server/stats/pull/StatsPullAtomService.java +++ b/services/core/java/com/android/server/stats/pull/StatsPullAtomService.java @@ -18,20 +18,17 @@ package com.android.server.stats.pull; import static android.app.AppOpsManager.OP_FLAG_SELF; import static android.app.AppOpsManager.OP_FLAG_TRUSTED_PROXIED; -import static android.app.usage.NetworkStatsManager.FLAG_AUGMENT_WITH_SUBSCRIPTION_PLAN; -import static android.app.usage.NetworkStatsManager.FLAG_POLL_FORCE; -import static android.app.usage.NetworkStatsManager.FLAG_POLL_ON_OPEN; import static android.content.pm.PackageInfo.REQUESTED_PERMISSION_GRANTED; import static android.content.pm.PermissionInfo.PROTECTION_DANGEROUS; import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR; import static android.net.NetworkCapabilities.TRANSPORT_WIFI; -import static android.net.NetworkIdentity.OEM_PAID; -import static android.net.NetworkIdentity.OEM_PRIVATE; import static android.net.NetworkStats.METERED_YES; import static android.net.NetworkTemplate.MATCH_ETHERNET; import static android.net.NetworkTemplate.MATCH_MOBILE; import static android.net.NetworkTemplate.MATCH_WIFI; import static android.net.NetworkTemplate.OEM_MANAGED_ALL; +import static android.net.NetworkTemplate.OEM_MANAGED_PAID; +import static android.net.NetworkTemplate.OEM_MANAGED_PRIVATE; import static android.net.NetworkTemplate.getAllCollapsedRatTypes; import static android.os.Debug.getIonHeapsSizeKb; import static android.os.Process.LAST_SHARED_APPLICATION_GID; @@ -73,6 +70,7 @@ import android.app.ProcessMemoryState; import android.app.RuntimeAppOpAccessMessage; import android.app.StatsManager; import android.app.StatsManager.PullAtomMetadata; +import android.app.usage.NetworkStatsManager; import android.bluetooth.BluetoothActivityEnergyInfo; import android.bluetooth.BluetoothAdapter; import android.bluetooth.UidTraffic; @@ -86,8 +84,6 @@ import android.hardware.biometrics.BiometricsProtoEnums; import android.hardware.face.FaceManager; import android.hardware.fingerprint.FingerprintManager; import android.net.ConnectivityManager; -import android.net.INetworkStatsService; -import android.net.INetworkStatsSession; import android.net.Network; import android.net.NetworkRequest; import android.net.NetworkStats; @@ -181,6 +177,7 @@ import com.android.internal.os.StoragedUidIoStatsReader; import com.android.internal.os.SystemServerCpuThreadReader.SystemServiceCpuThreadTimes; import com.android.internal.util.CollectionUtils; import com.android.internal.util.FrameworkStatsLog; +import com.android.net.module.util.NetworkStatsUtils; import com.android.role.RoleManagerLocal; import com.android.server.BinderCallsStatsService; import com.android.server.LocalManagerRegistry; @@ -228,7 +225,7 @@ import java.util.concurrent.Executor; import java.util.concurrent.ThreadLocalRandom; import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeoutException; -import java.util.function.BiConsumer; +import java.util.function.Function; /** * SystemService containing PullAtomCallbacks that are registered with statsd. @@ -324,6 +321,7 @@ public class StatsPullAtomService extends SystemService { private WifiManager mWifiManager; private TelephonyManager mTelephony; private SubscriptionManager mSubscriptionManager; + private NetworkStatsManager mNetworkStatsManager; @GuardedBy("mKernelWakelockLock") private KernelWakelockReader mKernelWakelockReader; @@ -769,7 +767,7 @@ public class StatsPullAtomService extends SystemService { mContext.getSystemService(Context.TELEPHONY_SUBSCRIPTION_SERVICE); mStatsSubscriptionsListener = new StatsSubscriptionsListener(mSubscriptionManager); mStorageManager = (StorageManager) mContext.getSystemService(StorageManager.class); - + mNetworkStatsManager = mContext.getSystemService(NetworkStatsManager.class); // Initialize DiskIO mStoragedUidIoStatsReader = new StoragedUidIoStatsReader(); @@ -959,32 +957,6 @@ public class StatsPullAtomService extends SystemService { registerOemManagedBytesTransfer(); } - /** - * Return the {@code INetworkStatsSession} object that holds the necessary properties needed - * for the subsequent queries to {@link com.android.server.net.NetworkStatsService}. Or - * null if the service or binder cannot be obtained. Calling this method will trigger poll - * in NetworkStatsService with once per 15 seconds rate-limit, unless {@code bypassRateLimit} - * is set to true. This is needed in {@link #getUidNetworkStatsSnapshotForTemplate}, where - * bypassing the limit is necessary for perfd to supply realtime stats to developers looking at - * the network usage of their app. - */ - @Nullable - private INetworkStatsSession getNetworkStatsSession(boolean bypassRateLimit) { - final INetworkStatsService networkStatsService = - INetworkStatsService.Stub.asInterface( - ServiceManager.getService(Context.NETWORK_STATS_SERVICE)); - if (networkStatsService == null) return null; - - try { - return networkStatsService.openSessionForUsageStats( - FLAG_AUGMENT_WITH_SUBSCRIPTION_PLAN | (bypassRateLimit ? FLAG_POLL_FORCE - : FLAG_POLL_ON_OPEN), mContext.getOpPackageName()); - } catch (RemoteException e) { - Slog.e(TAG, "Cannot get NetworkStats session", e); - return null; - } - } - private IThermalService getIThermalService() { synchronized (mThermalLock) { if (mThermalService == null) { @@ -1115,8 +1087,8 @@ public class StatsPullAtomService extends SystemService { case FrameworkStatsLog.WIFI_BYTES_TRANSFER: { final NetworkStats stats = getUidNetworkStatsSnapshotForTransport(TRANSPORT_WIFI); if (stats != null) { - ret.add(new NetworkStatsExt(stats.groupedByUid(), new int[] {TRANSPORT_WIFI}, - /*slicedByFgbg=*/false)); + ret.add(new NetworkStatsExt(sliceNetworkStatsByUid(stats), + new int[] {TRANSPORT_WIFI}, /*slicedByFgbg=*/false)); } break; } @@ -1132,7 +1104,7 @@ public class StatsPullAtomService extends SystemService { final NetworkStats stats = getUidNetworkStatsSnapshotForTransport(TRANSPORT_CELLULAR); if (stats != null) { - ret.add(new NetworkStatsExt(stats.groupedByUid(), + ret.add(new NetworkStatsExt(sliceNetworkStatsByUid(stats), new int[] {TRANSPORT_CELLULAR}, /*slicedByFgbg=*/false)); } break; @@ -1223,23 +1195,19 @@ public class StatsPullAtomService extends SystemService { private void addNetworkStats(int atomTag, @NonNull List<StatsEvent> ret, @NonNull NetworkStatsExt statsExt) { - int size = statsExt.stats.size(); - final NetworkStats.Entry entry = new NetworkStats.Entry(); // For recycling - for (int j = 0; j < size; j++) { - statsExt.stats.getValues(j, entry); + for (NetworkStats.Entry entry : statsExt.stats) { StatsEvent statsEvent; - if (statsExt.slicedByFgbg) { // MobileBytesTransferByFgBg atom or WifiBytesTransferByFgBg atom. statsEvent = FrameworkStatsLog.buildStatsEvent( - atomTag, entry.uid, - (entry.set > 0), entry.rxBytes, entry.rxPackets, entry.txBytes, - entry.txPackets); + atomTag, entry.getUid(), + (entry.getSet() > 0), entry.getRxBytes(), entry.getRxPackets(), + entry.getTxBytes(), entry.getTxPackets()); } else { // MobileBytesTransfer atom or WifiBytesTransfer atom. statsEvent = FrameworkStatsLog.buildStatsEvent( - atomTag, entry.uid, entry.rxBytes, - entry.rxPackets, entry.txBytes, entry.txPackets); + atomTag, entry.getUid(), entry.getRxBytes(), + entry.getRxPackets(), entry.getTxBytes(), entry.getTxPackets()); } ret.add(statsEvent); } @@ -1247,13 +1215,12 @@ public class StatsPullAtomService extends SystemService { private void addBytesTransferByTagAndMeteredAtoms(@NonNull NetworkStatsExt statsExt, @NonNull List<StatsEvent> pulledData) { - final NetworkStats.Entry entry = new NetworkStats.Entry(); // for recycling - for (int i = 0; i < statsExt.stats.size(); i++) { - statsExt.stats.getValues(i, entry); + for (NetworkStats.Entry entry : statsExt.stats) { pulledData.add(FrameworkStatsLog.buildStatsEvent( - FrameworkStatsLog.BYTES_TRANSFER_BY_TAG_AND_METERED, entry.uid, - entry.metered == NetworkStats.METERED_YES, entry.tag, entry.rxBytes, - entry.rxPackets, entry.txBytes, entry.txPackets)); + FrameworkStatsLog.BYTES_TRANSFER_BY_TAG_AND_METERED, entry.getUid(), + entry.getMetered() == NetworkStats.METERED_YES, entry.getTag(), + entry.getRxBytes(), entry.getRxPackets(), entry.getTxBytes(), + entry.getTxPackets())); } } @@ -1268,12 +1235,11 @@ public class StatsPullAtomService extends SystemService { // Report NR connected in 5G non-standalone mode, or if the RAT type is NR to begin with. final boolean isNR = is5GNsa || statsExt.ratType == TelephonyManager.NETWORK_TYPE_NR; - final NetworkStats.Entry entry = new NetworkStats.Entry(); // for recycling - for (int i = 0; i < statsExt.stats.size(); i++) { - statsExt.stats.getValues(i, entry); + for (NetworkStats.Entry entry : statsExt.stats) { pulledData.add(FrameworkStatsLog.buildStatsEvent( - FrameworkStatsLog.DATA_USAGE_BYTES_TRANSFER, entry.set, entry.rxBytes, - entry.rxPackets, entry.txBytes, entry.txPackets, + FrameworkStatsLog.DATA_USAGE_BYTES_TRANSFER, + entry.getSet(), entry.getRxBytes(), entry.getRxPackets(), + entry.getTxBytes(), entry.getTxPackets(), is5GNsa ? TelephonyManager.NETWORK_TYPE_LTE : statsExt.ratType, // Fill information about subscription, these cannot be null since invalid data // would be filtered when adding into subInfo list. @@ -1287,22 +1253,21 @@ public class StatsPullAtomService extends SystemService { private void addOemDataUsageBytesTransferAtoms(@NonNull NetworkStatsExt statsExt, @NonNull List<StatsEvent> pulledData) { - final NetworkStats.Entry entry = new NetworkStats.Entry(); // for recycling final int oemManaged = statsExt.oemManaged; for (final int transport : statsExt.transports) { - for (int i = 0; i < statsExt.stats.size(); i++) { - statsExt.stats.getValues(i, entry); + for (NetworkStats.Entry entry : statsExt.stats) { pulledData.add(FrameworkStatsLog.buildStatsEvent( - FrameworkStatsLog.OEM_MANAGED_BYTES_TRANSFER, entry.uid, (entry.set > 0), - oemManaged, transport, entry.rxBytes, entry.rxPackets, entry.txBytes, - entry.txPackets)); + FrameworkStatsLog.OEM_MANAGED_BYTES_TRANSFER, entry.getUid(), + (entry.getSet() > 0), oemManaged, transport, entry.getRxBytes(), + entry.getRxPackets(), entry.getTxBytes(), entry.getTxPackets())); } } } @NonNull private List<NetworkStatsExt> getDataUsageBytesTransferSnapshotForOemManaged() { final int[] matchRules = new int[] {MATCH_ETHERNET, MATCH_MOBILE, MATCH_WIFI}; - final int[] oemManagedTypes = new int[] {OEM_PAID | OEM_PRIVATE, OEM_PAID, OEM_PRIVATE}; + final int[] oemManagedTypes = new int[] {OEM_MANAGED_PAID | OEM_MANAGED_PRIVATE, + OEM_MANAGED_PAID, OEM_MANAGED_PRIVATE}; final List<NetworkStatsExt> ret = new ArrayList<>(); @@ -1357,22 +1322,32 @@ public class StatsPullAtomService extends SystemService { final long currentTimeInMillis = MICROSECONDS.toMillis(SystemClock.currentTimeMicro()); final long bucketDuration = Settings.Global.getLong(mContext.getContentResolver(), NETSTATS_UID_BUCKET_DURATION, NETSTATS_UID_DEFAULT_BUCKET_DURATION_MS); - try { - // TODO (b/156313635): This is short-term hack to allow perfd gets updated networkStats - // history when query in every second in order to show realtime statistics. However, - // this is not a good long-term solution since NetworkStatsService will make frequent - // I/O and also block main thread when polling. - // Consider making perfd queries NetworkStatsService directly. - final NetworkStats stats = getNetworkStatsSession(template.getMatchRule() - == NetworkTemplate.MATCH_WIFI_WILDCARD).getSummaryForAllUid(template, - currentTimeInMillis - elapsedMillisSinceBoot - bucketDuration, - currentTimeInMillis, includeTags); - return stats; - } catch (RemoteException | NullPointerException e) { - Slog.e(TAG, "Pulling netstats for template=" + template + " and includeTags=" - + includeTags + " causes error", e); + + // TODO (b/156313635): This is short-term hack to allow perfd gets updated networkStats + // history when query in every second in order to show realtime statistics. However, + // this is not a good long-term solution since NetworkStatsService will make frequent + // I/O and also block main thread when polling. + // Consider making perfd queries NetworkStatsService directly. + if (template.getMatchRule() == MATCH_WIFI && template.getSubscriberIds().isEmpty()) { + mNetworkStatsManager.forceUpdate(); } - return null; + + final android.app.usage.NetworkStats queryNonTaggedStats = + mNetworkStatsManager.querySummary( + template, currentTimeInMillis - elapsedMillisSinceBoot - bucketDuration, + currentTimeInMillis); + + final NetworkStats nonTaggedStats = + NetworkStatsUtils.fromPublicNetworkStats(queryNonTaggedStats); + if (!includeTags) return nonTaggedStats; + + final android.app.usage.NetworkStats queryTaggedStats = + mNetworkStatsManager.queryTaggedSummary(template, + currentTimeInMillis - elapsedMillisSinceBoot - bucketDuration, + currentTimeInMillis); + final NetworkStats taggedStats = + NetworkStatsUtils.fromPublicNetworkStats(queryTaggedStats); + return nonTaggedStats.add(taggedStats); } @NonNull private List<NetworkStatsExt> getDataUsageBytesTransferSnapshotForSub( @@ -1396,27 +1371,51 @@ public class StatsPullAtomService extends SystemService { return ret; } + @NonNull private NetworkStats sliceNetworkStatsByUid(@NonNull NetworkStats stats) { + return sliceNetworkStats(stats, + (entry) -> { + return new NetworkStats.Entry(null /* IFACE_ALL */, entry.getUid(), + NetworkStats.SET_ALL, NetworkStats.TAG_NONE, + NetworkStats.METERED_ALL, NetworkStats.ROAMING_ALL, + NetworkStats.DEFAULT_NETWORK_ALL, + entry.getRxBytes(), entry.getRxPackets(), + entry.getTxBytes(), entry.getTxPackets(), 0); + }); + } + @NonNull private NetworkStats sliceNetworkStatsByFgbg(@NonNull NetworkStats stats) { return sliceNetworkStats(stats, - (newEntry, oldEntry) -> { - newEntry.set = oldEntry.set; + (entry) -> { + return new NetworkStats.Entry(null /* IFACE_ALL */, NetworkStats.UID_ALL, + entry.getSet(), NetworkStats.TAG_NONE, + NetworkStats.METERED_ALL, NetworkStats.ROAMING_ALL, + NetworkStats.DEFAULT_NETWORK_ALL, + entry.getRxBytes(), entry.getRxPackets(), + entry.getTxBytes(), entry.getTxPackets(), 0); }); } @NonNull private NetworkStats sliceNetworkStatsByUidAndFgbg(@NonNull NetworkStats stats) { return sliceNetworkStats(stats, - (newEntry, oldEntry) -> { - newEntry.uid = oldEntry.uid; - newEntry.set = oldEntry.set; + (entry) -> { + return new NetworkStats.Entry(null /* IFACE_ALL */, entry.getUid(), + entry.getSet(), NetworkStats.TAG_NONE, + NetworkStats.METERED_ALL, NetworkStats.ROAMING_ALL, + NetworkStats.DEFAULT_NETWORK_ALL, + entry.getRxBytes(), entry.getRxPackets(), + entry.getTxBytes(), entry.getTxPackets(), 0); }); } @NonNull private NetworkStats sliceNetworkStatsByUidTagAndMetered(@NonNull NetworkStats stats) { return sliceNetworkStats(stats, - (newEntry, oldEntry) -> { - newEntry.uid = oldEntry.uid; - newEntry.tag = oldEntry.tag; - newEntry.metered = oldEntry.metered; + (entry) -> { + return new NetworkStats.Entry(null /* IFACE_ALL */, entry.getUid(), + NetworkStats.SET_ALL, entry.getTag(), + entry.getMetered(), NetworkStats.ROAMING_ALL, + NetworkStats.DEFAULT_NETWORK_ALL, + entry.getRxBytes(), entry.getRxPackets(), + entry.getTxBytes(), entry.getTxPackets(), 0); }); } @@ -1426,46 +1425,31 @@ public class StatsPullAtomService extends SystemService { * * This function iterates through each NetworkStats.Entry, sets its dimensions equal to the * default state (with the presumption that we don't want to slice on anything), and then - * applies the slicer lambda to allow users to control which dimensions to slice on. This is - * adapted from groupedByUid within NetworkStats.java + * applies the slicer lambda to allow users to control which dimensions to slice on. * - * @param slicer An operation taking into two parameters, new NetworkStats.Entry and old - * NetworkStats.Entry, that should be used to copy state from the old to the new. + * @param slicer An operation taking one parameter, NetworkStats.Entry, that should be used to + * get the state from entry to replace the default value. * This is useful for slicing by particular dimensions. For example, if we wished * to slice by uid and tag, we could write the following lambda: - * (new, old) -> { - * new.uid = old.uid; - * new.tag = old.tag; + * (entry) -> { + * return new NetworkStats.Entry(null, entry.getUid(), + * NetworkStats.SET_ALL, entry.getTag(), + * NetworkStats.METERED_ALL, NetworkStats.ROAMING_ALL, + * NetworkStats.DEFAULT_NETWORK_ALL, + * entry.getRxBytes(), entry.getRxPackets(), + * entry.getTxBytes(), entry.getTxPackets(), 0); * } - * If no slicer is provided, the data is not sliced by any dimensions. * @return new NeworkStats object appropriately sliced */ @NonNull private NetworkStats sliceNetworkStats(@NonNull NetworkStats stats, - @Nullable BiConsumer<NetworkStats.Entry, NetworkStats.Entry> slicer) { - final NetworkStats ret = new NetworkStats(stats.getElapsedRealtime(), 1); - - final NetworkStats.Entry entry = new NetworkStats.Entry(); - entry.uid = NetworkStats.UID_ALL; - entry.iface = NetworkStats.IFACE_ALL; - entry.set = NetworkStats.SET_ALL; - entry.tag = NetworkStats.TAG_NONE; - entry.metered = NetworkStats.METERED_ALL; - entry.roaming = NetworkStats.ROAMING_ALL; - entry.defaultNetwork = NetworkStats.DEFAULT_NETWORK_ALL; - - final NetworkStats.Entry recycle = new NetworkStats.Entry(); // used for retrieving values - for (int i = 0; i < stats.size(); i++) { - stats.getValues(i, recycle); + @NonNull Function<NetworkStats.Entry, NetworkStats.Entry> slicer) { + NetworkStats ret = new NetworkStats(0, 1); + NetworkStats.Entry entry = new NetworkStats.Entry(); + for (NetworkStats.Entry e : stats) { if (slicer != null) { - slicer.accept(entry, recycle); + entry = slicer.apply(e); } - - entry.rxBytes = recycle.rxBytes; - entry.rxPackets = recycle.rxPackets; - entry.txBytes = recycle.txBytes; - entry.txPackets = recycle.txPackets; - // Operations purposefully omitted since we don't use them for statsd. - ret.combineValues(entry); + ret = ret.addEntry(entry); } return ret; } diff --git a/services/core/jni/Android.bp b/services/core/jni/Android.bp index e7005daf5626..e48b5e17739b 100644 --- a/services/core/jni/Android.bp +++ b/services/core/jni/Android.bp @@ -141,8 +141,8 @@ cc_defaults { "libutils", "libhwui", "libbpf_android", - "libnetdbpf", "libnetdutils", + "libnetworkstats", "libpsi", "libdataloader", "libincfs", diff --git a/services/core/jni/com_android_server_UsbAlsaJackDetector.cpp b/services/core/jni/com_android_server_UsbAlsaJackDetector.cpp index ccb4f5995330..cba54b39fe9a 100644 --- a/services/core/jni/com_android_server_UsbAlsaJackDetector.cpp +++ b/services/core/jni/com_android_server_UsbAlsaJackDetector.cpp @@ -25,7 +25,6 @@ #include <stdio.h> #include <string.h> -#include <asm/byteorder.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> diff --git a/services/core/jni/com_android_server_UsbDescriptorParser.cpp b/services/core/jni/com_android_server_UsbDescriptorParser.cpp index d29d3fcb51d5..9917bcb45c0a 100644 --- a/services/core/jni/com_android_server_UsbDescriptorParser.cpp +++ b/services/core/jni/com_android_server_UsbDescriptorParser.cpp @@ -15,16 +15,14 @@ */ #define LOG_TAG "UsbHostManagerJNI" -#include "utils/Log.h" - +#include <nativehelper/JNIHelp.h> #include <stdlib.h> +#include <usbhost/usbhost.h> +#include <usbhost/usbhost_jni.h> #include "jni.h" -#include <nativehelper/JNIHelp.h> - -#include <usbhost/usbhost.h> +#include "utils/Log.h" -#define MAX_DESCRIPTORS_LENGTH 4096 static const int USB_CONTROL_TRANSFER_TIMEOUT_MS = 200; // com.android.server.usb.descriptors @@ -41,26 +39,9 @@ jbyteArray JNICALL Java_com_android_server_usb_descriptors_UsbDescriptorParser_g } int fd = usb_device_get_fd(device); - if (fd < 0) { - usb_device_close(device); - return NULL; - } - - // from android_hardware_UsbDeviceConnection_get_desc() - jbyte buffer[MAX_DESCRIPTORS_LENGTH]; - lseek(fd, 0, SEEK_SET); - int numBytes = read(fd, buffer, sizeof(buffer)); - jbyteArray ret = NULL; + jbyteArray descriptors = usb_jni_read_descriptors(env, fd); usb_device_close(device); - - if (numBytes > 0) { - ret = env->NewByteArray(numBytes); - env->SetByteArrayRegion(ret, 0, numBytes, buffer); - } else { - ALOGE("error reading descriptors\n"); - } - - return ret; + return descriptors; } jstring JNICALL Java_com_android_server_usb_descriptors_UsbDescriptorParser_getDescriptorString_1native( diff --git a/services/core/jni/com_android_server_UsbDeviceManager.cpp b/services/core/jni/com_android_server_UsbDeviceManager.cpp index 3ab5920d8b59..0a9ce2fed7fc 100644 --- a/services/core/jni/com_android_server_UsbDeviceManager.cpp +++ b/services/core/jni/com_android_server_UsbDeviceManager.cpp @@ -25,7 +25,6 @@ #include "MtpDescriptors.h" #include <stdio.h> -#include <asm/byteorder.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> diff --git a/services/core/jni/com_android_server_UsbHostManager.cpp b/services/core/jni/com_android_server_UsbHostManager.cpp index a629b69c1c27..e29d2ca663f7 100644 --- a/services/core/jni/com_android_server_UsbHostManager.cpp +++ b/services/core/jni/com_android_server_UsbHostManager.cpp @@ -23,7 +23,6 @@ #include "android_runtime/Log.h" #include <stdio.h> -#include <asm/byteorder.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> @@ -31,8 +30,6 @@ #include <usbhost/usbhost.h> -#define MAX_DESCRIPTORS_LENGTH 4096 - namespace android { diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java b/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java index 37a84f3698c1..1c9d58458629 100644 --- a/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java +++ b/services/devicepolicy/java/com/android/server/devicepolicy/ActiveAdmin.java @@ -32,6 +32,7 @@ import android.app.admin.DeviceAdminInfo; import android.app.admin.DevicePolicyManager; import android.app.admin.FactoryResetProtectionPolicy; import android.app.admin.PasswordPolicy; +import android.app.admin.PreferentialNetworkServiceConfig; import android.graphics.Color; import android.os.Bundle; import android.os.PersistableBundle; @@ -294,6 +295,8 @@ class ActiveAdmin { public boolean mAdminCanGrantSensorsPermissions; public boolean mPreferentialNetworkServiceEnabled = DevicePolicyManager.PREFERENTIAL_NETWORK_SERVICE_ENABLED_DEFAULT; + public PreferentialNetworkServiceConfig mPreferentialNetworkServiceConfig = + PreferentialNetworkServiceConfig.DEFAULT; private static final boolean USB_DATA_SIGNALING_ENABLED_DEFAULT = true; boolean mUsbDataSignalingEnabled = USB_DATA_SIGNALING_ENABLED_DEFAULT; diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java index df98390ddf05..564b60825ab0 100644 --- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java +++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java @@ -109,6 +109,8 @@ import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; import static android.content.pm.PackageManager.MATCH_UNINSTALLED_PACKAGES; import static android.net.ConnectivityManager.PROFILE_NETWORK_PREFERENCE_DEFAULT; import static android.net.ConnectivityManager.PROFILE_NETWORK_PREFERENCE_ENTERPRISE; +import static android.net.ConnectivityManager.PROFILE_NETWORK_PREFERENCE_ENTERPRISE_NO_FALLBACK; +import static android.net.NetworkCapabilities.NET_ENTERPRISE_ID_1; import static android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK; import static android.provider.Settings.Global.PRIVATE_DNS_SPECIFIER; import static android.provider.Settings.Secure.USER_SETUP_COMPLETE; @@ -179,6 +181,7 @@ import android.app.admin.NetworkEvent; import android.app.admin.ParcelableGranteeMap; import android.app.admin.PasswordMetrics; import android.app.admin.PasswordPolicy; +import android.app.admin.PreferentialNetworkServiceConfig; import android.app.admin.SecurityLog; import android.app.admin.SecurityLog.SecurityEvent; import android.app.admin.StartInstallingUpdateCallback; @@ -3277,14 +3280,14 @@ public class DevicePolicyManagerService extends BaseIDevicePolicyManager { updatePermissionPolicyCache(userId); updateAdminCanGrantSensorsPermissionCache(userId); - final boolean preferentialNetworkServiceEnabled; + final PreferentialNetworkServiceConfig preferentialNetworkServiceConfig; synchronized (getLockObject()) { ActiveAdmin owner = getDeviceOrProfileOwnerAdminLocked(userId); - preferentialNetworkServiceEnabled = owner != null - ? owner.mPreferentialNetworkServiceEnabled - : DevicePolicyManager.PREFERENTIAL_NETWORK_SERVICE_ENABLED_DEFAULT; + preferentialNetworkServiceConfig = owner != null + ? owner.mPreferentialNetworkServiceConfig + : PreferentialNetworkServiceConfig.DEFAULT; } - updateNetworkPreferenceForUser(userId, preferentialNetworkServiceEnabled); + updateNetworkPreferenceForUser(userId, preferentialNetworkServiceConfig); startOwnerService(userId, "start-user"); } @@ -3301,7 +3304,7 @@ public class DevicePolicyManagerService extends BaseIDevicePolicyManager { @Override void handleStopUser(int userId) { - updateNetworkPreferenceForUser(userId, false); + updateNetworkPreferenceForUser(userId, PreferentialNetworkServiceConfig.DEFAULT); stopOwnerService(userId, "stop-user"); } @@ -11845,7 +11848,7 @@ public class DevicePolicyManagerService extends BaseIDevicePolicyManager { final CallerIdentity caller = getCallerIdentity(); Preconditions.checkCallAuthorization(isProfileOwner(caller), "Caller is not profile owner;" - + " only profile owner may control the preferntial network service"); + + " only profile owner may control the preferential network service"); synchronized (getLockObject()) { final ActiveAdmin requiredAdmin = getProfileOwnerAdminLocked( caller.getUserId()); @@ -11882,6 +11885,47 @@ public class DevicePolicyManagerService extends BaseIDevicePolicyManager { } @Override + public void setPreferentialNetworkServiceConfig( + PreferentialNetworkServiceConfig preferentialNetworkServiceConfig) { + if (!mHasFeature) { + return; + } + final CallerIdentity caller = getCallerIdentity(); + Preconditions.checkCallAuthorization(isProfileOwner(caller), + "Caller is not profile owner;" + + " only profile owner may control the preferential network service"); + synchronized (getLockObject()) { + final ActiveAdmin requiredAdmin = getProfileOwnerAdminLocked( + caller.getUserId()); + if (!requiredAdmin.mPreferentialNetworkServiceConfig.equals( + preferentialNetworkServiceConfig)) { + requiredAdmin.mPreferentialNetworkServiceConfig = preferentialNetworkServiceConfig; + saveSettingsLocked(caller.getUserId()); + } + } + updateNetworkPreferenceForUser(caller.getUserId(), preferentialNetworkServiceConfig); + DevicePolicyEventLogger + .createEvent(DevicePolicyEnums.SET_PREFERENTIAL_NETWORK_SERVICE_ENABLED) + .setBoolean(preferentialNetworkServiceConfig.isEnabled()) + .write(); + } + + @Override + public PreferentialNetworkServiceConfig getPreferentialNetworkServiceConfig() { + if (!mHasFeature) { + return PreferentialNetworkServiceConfig.DEFAULT; + } + + final CallerIdentity caller = getCallerIdentity(); + Preconditions.checkCallAuthorization(isProfileOwner(caller), + "Caller is not profile owner"); + synchronized (getLockObject()) { + final ActiveAdmin requiredAdmin = getProfileOwnerAdminLocked(caller.getUserId()); + return requiredAdmin.mPreferentialNetworkServiceConfig; + } + } + + @Override public void setLockTaskPackages(ComponentName who, String[] packages) throws SecurityException { Objects.requireNonNull(who, "ComponentName is null"); @@ -17537,11 +17581,48 @@ public class DevicePolicyManagerService extends BaseIDevicePolicyManager { if (!isManagedProfile(userId)) { return; } - int networkPreference = preferentialNetworkServiceEnabled - ? PROFILE_NETWORK_PREFERENCE_ENTERPRISE : PROFILE_NETWORK_PREFERENCE_DEFAULT; ProfileNetworkPreference.Builder preferenceBuilder = new ProfileNetworkPreference.Builder(); - preferenceBuilder.setPreference(networkPreference); + if (preferentialNetworkServiceEnabled) { + preferenceBuilder.setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE); + preferenceBuilder.setPreferenceEnterpriseId(NET_ENTERPRISE_ID_1); + } else { + preferenceBuilder.setPreference(PROFILE_NETWORK_PREFERENCE_DEFAULT); + } + List<ProfileNetworkPreference> preferences = new ArrayList<>(); + preferences.add(preferenceBuilder.build()); + mInjector.binderWithCleanCallingIdentity(() -> + mInjector.getConnectivityManager().setProfileNetworkPreferences( + UserHandle.of(userId), preferences, + null /* executor */, null /* listener */)); + } + + private void updateNetworkPreferenceForUser(int userId, + PreferentialNetworkServiceConfig preferentialNetworkServiceConfig) { + if (!isManagedProfile(userId)) { + return; + } + ProfileNetworkPreference.Builder preferenceBuilder = + new ProfileNetworkPreference.Builder(); + if (preferentialNetworkServiceConfig.isEnabled()) { + if (preferentialNetworkServiceConfig.isFallbackToDefaultConnectionAllowed()) { + preferenceBuilder.setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE); + } else { + preferenceBuilder.setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE_NO_FALLBACK); + } + } else { + preferenceBuilder.setPreference(PROFILE_NETWORK_PREFERENCE_DEFAULT); + } + List<Integer> allowedUids = Arrays.stream( + preferentialNetworkServiceConfig.getIncludedUids()).boxed().collect( + Collectors.toList()); + List<Integer> excludedUids = Arrays.stream( + preferentialNetworkServiceConfig.getExcludedUids()).boxed().collect( + Collectors.toList()); + preferenceBuilder.setIncludedUids(allowedUids); + preferenceBuilder.setExcludedUids(excludedUids); + preferenceBuilder.setPreferenceEnterpriseId( + preferentialNetworkServiceConfig.getNetworkId()); List<ProfileNetworkPreference> preferences = new ArrayList<>(); preferences.add(preferenceBuilder.build()); mInjector.binderWithCleanCallingIdentity(() -> diff --git a/services/java/com/android/server/SystemServer.java b/services/java/com/android/server/SystemServer.java index 554a7b1bd574..710a9cf74112 100644 --- a/services/java/com/android/server/SystemServer.java +++ b/services/java/com/android/server/SystemServer.java @@ -54,6 +54,7 @@ import android.hardware.display.DisplayManagerInternal; import android.net.ConnectivityManager; import android.net.ConnectivityModuleConnector; import android.net.NetworkStackClient; +import android.net.TrafficStats; import android.os.BaseBundle; import android.os.Binder; import android.os.Build; @@ -1838,6 +1839,7 @@ public final class SystemServer implements Dumpable { try { networkStats = NetworkStatsService.create(context); ServiceManager.addService(Context.NETWORK_STATS_SERVICE, networkStats); + TrafficStats.init(context); } catch (Throwable e) { reportWtf("starting NetworkStats Service", e); } diff --git a/services/tests/servicestests/src/com/android/server/devicepolicy/DevicePolicyManagerTest.java b/services/tests/servicestests/src/com/android/server/devicepolicy/DevicePolicyManagerTest.java index a63aa6a918d7..3511fc1c36d5 100644 --- a/services/tests/servicestests/src/com/android/server/devicepolicy/DevicePolicyManagerTest.java +++ b/services/tests/servicestests/src/com/android/server/devicepolicy/DevicePolicyManagerTest.java @@ -39,7 +39,9 @@ import static android.app.admin.PasswordMetrics.computeForPasswordOrPin; import static android.content.pm.ApplicationInfo.PRIVATE_FLAG_DIRECT_BOOT_AWARE; import static android.net.ConnectivityManager.PROFILE_NETWORK_PREFERENCE_DEFAULT; import static android.net.ConnectivityManager.PROFILE_NETWORK_PREFERENCE_ENTERPRISE; +import static android.net.ConnectivityManager.PROFILE_NETWORK_PREFERENCE_ENTERPRISE_NO_FALLBACK; import static android.net.InetAddresses.parseNumericAddress; +import static android.net.NetworkCapabilities.NET_ENTERPRISE_ID_1; import static com.android.internal.widget.LockPatternUtils.CREDENTIAL_TYPE_NONE; import static com.android.internal.widget.LockPatternUtils.EscrowTokenStateChangeCallback; @@ -89,6 +91,7 @@ import android.app.admin.DevicePolicyManagerInternal; import android.app.admin.DevicePolicyManagerLiteInternal; import android.app.admin.FactoryResetProtectionPolicy; import android.app.admin.PasswordMetrics; +import android.app.admin.PreferentialNetworkServiceConfig; import android.app.admin.SystemUpdatePolicy; import android.content.BroadcastReceiver; import android.content.ComponentName; @@ -4109,6 +4112,7 @@ public class DevicePolicyManagerTest extends DpmTestBase { ProfileNetworkPreference preferenceDetails2 = new ProfileNetworkPreference.Builder() .setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE) + .setPreferenceEnterpriseId(NET_ENTERPRISE_ID_1) .build(); List<ProfileNetworkPreference> preferences2 = new ArrayList<>(); preferences2.add(preferenceDetails); @@ -4118,6 +4122,164 @@ public class DevicePolicyManagerTest extends DpmTestBase { } @Test + public void testSetPreferentialNetworkServiceConfig_noProfileOwner() throws Exception { + assertExpectException(SecurityException.class, null, + () -> dpm.setPreferentialNetworkServiceConfig( + PreferentialNetworkServiceConfig.DEFAULT)); + } + + @Test + public void testIsPreferentialNetworkServiceEnabled_noProfileOwner() throws Exception { + assertExpectException(SecurityException.class, null, + () -> dpm.isPreferentialNetworkServiceEnabled()); + } + + @Test + public void testSetPreferentialNetworkServiceConfig_invalidConfig() throws Exception { + final int managedProfileUserId = 15; + final int managedProfileAdminUid = UserHandle.getUid(managedProfileUserId, 19436); + addManagedProfile(admin1, managedProfileAdminUid, admin1); + mContext.binder.callingUid = managedProfileAdminUid; + + PreferentialNetworkServiceConfig.Builder preferentialNetworkServiceConfigBuilder = + new PreferentialNetworkServiceConfig.Builder(); + assertExpectException(NullPointerException.class, null, + () -> preferentialNetworkServiceConfigBuilder.setIncludedUids(null)); + assertExpectException(NullPointerException.class, null, + () -> preferentialNetworkServiceConfigBuilder.setExcludedUids(null)); + assertExpectException(IllegalArgumentException.class, null, + () -> preferentialNetworkServiceConfigBuilder.setNetworkId(6)); + int[] includedUids = new int[]{1, 2}; + int[] excludedUids = new int[]{3, 4}; + preferentialNetworkServiceConfigBuilder.setIncludedUids(includedUids); + preferentialNetworkServiceConfigBuilder.setExcludedUids(excludedUids); + + assertExpectException(IllegalStateException.class, null, + () -> preferentialNetworkServiceConfigBuilder.build()); + } + + @Test + public void testSetPreferentialNetworkServiceConfig_defaultPreference() throws Exception { + final int managedProfileUserId = 15; + final int managedProfileAdminUid = UserHandle.getUid(managedProfileUserId, 19436); + addManagedProfile(admin1, managedProfileAdminUid, admin1); + mContext.binder.callingUid = managedProfileAdminUid; + + dpm.setPreferentialNetworkServiceConfig(PreferentialNetworkServiceConfig.DEFAULT); + assertThat(dpm.isPreferentialNetworkServiceEnabled()).isFalse(); + assertThat(dpm.getPreferentialNetworkServiceConfig() + .isEnabled()).isFalse(); + + ProfileNetworkPreference preferenceDetails = + new ProfileNetworkPreference.Builder() + .setPreference(PROFILE_NETWORK_PREFERENCE_DEFAULT) + .build(); + List<ProfileNetworkPreference> preferences = new ArrayList<>(); + preferences.add(preferenceDetails); + verify(getServices().connectivityManager, times(1)) + .setProfileNetworkPreferences(UserHandle.of(managedProfileUserId), preferences, + null, null); + } + + @Test + public void testSetPreferentialNetworkServiceConfig_enterprisePreference() throws Exception { + PreferentialNetworkServiceConfig preferentialNetworkServiceConfigEnabled = + (new PreferentialNetworkServiceConfig.Builder()) + .setEnabled(true) + .setNetworkId(NET_ENTERPRISE_ID_1) + .build(); + + final int managedProfileUserId = 15; + final int managedProfileAdminUid = UserHandle.getUid(managedProfileUserId, 19436); + addManagedProfile(admin1, managedProfileAdminUid, admin1); + mContext.binder.callingUid = managedProfileAdminUid; + + dpm.setPreferentialNetworkServiceConfig(preferentialNetworkServiceConfigEnabled); + assertThat(dpm.getPreferentialNetworkServiceConfig() + .isEnabled()).isTrue(); + ProfileNetworkPreference preferenceDetails = + new ProfileNetworkPreference.Builder() + .setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE) + .setPreferenceEnterpriseId(NET_ENTERPRISE_ID_1) + .build(); + List<ProfileNetworkPreference> preferences = new ArrayList<>(); + preferences.add(preferenceDetails); + verify(getServices().connectivityManager, times(1)) + .setProfileNetworkPreferences(UserHandle.of(managedProfileUserId), preferences, + null, null); + } + + @Test + public void testSetPreferentialNetworkServiceConfig_enterprisePreferenceIncludedUids() + throws Exception { + final int managedProfileUserId = 15; + final int managedProfileAdminUid = UserHandle.getUid(managedProfileUserId, 19436); + addManagedProfile(admin1, managedProfileAdminUid, admin1); + mContext.binder.callingUid = managedProfileAdminUid; + + PreferentialNetworkServiceConfig preferentialNetworkServiceConfigEnabled = + (new PreferentialNetworkServiceConfig.Builder()) + .setEnabled(true) + .setNetworkId(NET_ENTERPRISE_ID_1) + .setFallbackToDefaultConnectionAllowed(false) + .setIncludedUids(new int[]{1, 2}) + .build(); + dpm.setPreferentialNetworkServiceConfig(preferentialNetworkServiceConfigEnabled); + assertThat(dpm.getPreferentialNetworkServiceConfig() + .isEnabled()).isTrue(); + List<Integer> includedList = new ArrayList<>(); + includedList.add(1); + includedList.add(2); + ProfileNetworkPreference preferenceDetails = + new ProfileNetworkPreference.Builder() + .setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE_NO_FALLBACK) + .setPreferenceEnterpriseId(NET_ENTERPRISE_ID_1) + .setIncludedUids(includedList) + .build(); + List<ProfileNetworkPreference> preferences = new ArrayList<>(); + preferences.add(preferenceDetails); + verify(getServices().connectivityManager, times(1)) + .setProfileNetworkPreferences(UserHandle.of(managedProfileUserId), preferences, + null, null); + } + + @Test + public void testSetPreferentialNetworkServiceConfig_enterprisePreferenceExcludedUids() + throws Exception { + final int managedProfileUserId = 15; + final int managedProfileAdminUid = UserHandle.getUid(managedProfileUserId, 19436); + addManagedProfile(admin1, managedProfileAdminUid, admin1); + mContext.binder.callingUid = managedProfileAdminUid; + + PreferentialNetworkServiceConfig preferentialNetworkServiceConfigEnabled = + (new PreferentialNetworkServiceConfig.Builder()) + .setEnabled(true) + .setNetworkId(NET_ENTERPRISE_ID_1) + .setFallbackToDefaultConnectionAllowed(false) + .setExcludedUids(new int[]{1, 2}) + .build(); + + dpm.setPreferentialNetworkServiceConfig(preferentialNetworkServiceConfigEnabled); + assertThat(dpm.getPreferentialNetworkServiceConfig() + .isEnabled()).isTrue(); + List<Integer> excludedUids = new ArrayList<>(); + excludedUids.add(1); + excludedUids.add(2); + ProfileNetworkPreference preferenceDetails = + new ProfileNetworkPreference.Builder() + .setPreference(PROFILE_NETWORK_PREFERENCE_ENTERPRISE_NO_FALLBACK) + .setPreferenceEnterpriseId(NET_ENTERPRISE_ID_1) + .setExcludedUids(excludedUids) + .build(); + List<ProfileNetworkPreference> preferences = new ArrayList<>(); + preferences.clear(); + preferences.add(preferenceDetails); + verify(getServices().connectivityManager, times(1)) + .setProfileNetworkPreferences(UserHandle.of(managedProfileUserId), preferences, + null, null); + } + + @Test public void testSetSystemSettingFailWithNonWhitelistedSettings() throws Exception { mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; setupDeviceOwner(); diff --git a/services/tests/servicestests/src/com/android/server/net/NetworkPolicyManagerServiceTest.java b/services/tests/servicestests/src/com/android/server/net/NetworkPolicyManagerServiceTest.java index c544f5c2e245..e80721a10e90 100644 --- a/services/tests/servicestests/src/com/android/server/net/NetworkPolicyManagerServiceTest.java +++ b/services/tests/servicestests/src/com/android/server/net/NetworkPolicyManagerServiceTest.java @@ -51,6 +51,7 @@ import static android.net.NetworkPolicyManager.uidRulesToString; import static android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK; import static android.net.NetworkStats.METERED_NO; import static android.net.NetworkStats.METERED_YES; +import static android.net.NetworkTemplate.MATCH_MOBILE; import static android.net.NetworkTemplate.buildTemplateCarrierMetered; import static android.net.NetworkTemplate.buildTemplateWifi; import static android.net.TrafficStats.MB_IN_BYTES; @@ -71,7 +72,6 @@ import static com.android.server.net.NetworkPolicyManagerService.TYPE_LIMIT_SNOO import static com.android.server.net.NetworkPolicyManagerService.TYPE_RAPID; import static com.android.server.net.NetworkPolicyManagerService.TYPE_WARNING; import static com.android.server.net.NetworkPolicyManagerService.UidBlockedState.getEffectiveBlockedReasons; -import static com.android.server.net.NetworkStatsService.ACTION_NETWORK_STATS_UPDATED; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; @@ -95,6 +95,7 @@ import static org.mockito.Mockito.doNothing; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.never; import static org.mockito.Mockito.reset; +import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; @@ -495,8 +496,14 @@ public class NetworkPolicyManagerServiceTest { verify(mNetworkManager).registerObserver(networkObserver.capture()); mNetworkObserver = networkObserver.getValue(); - // Simulate NetworkStatsService broadcast stats updated to signal its readiness. - mServiceContext.sendBroadcast(new Intent(ACTION_NETWORK_STATS_UPDATED)); + // Catch UsageCallback during systemReady(). Simulate NetworkStatsService triggered + // stats updated callback to signal its readiness. + final ArgumentCaptor<NetworkStatsManager.UsageCallback> usageObserver = + ArgumentCaptor.forClass(NetworkStatsManager.UsageCallback.class); + verify(mStatsManager, times(2)) + .registerUsageCallback(any(), anyLong(), any(), usageObserver.capture()); + usageObserver.getValue().onThresholdReached( + new NetworkTemplate.Builder(MATCH_MOBILE).build()); NetworkPolicy defaultPolicy = mService.buildDefaultCarrierPolicy(0, ""); mDefaultWarningBytes = defaultPolicy.warningBytes; @@ -2046,7 +2053,7 @@ public class NetworkPolicyManagerServiceTest { private static NetworkStateSnapshot buildWifi() { WifiInfo mockWifiInfo = mock(WifiInfo.class); when(mockWifiInfo.makeCopy(anyLong())).thenReturn(mockWifiInfo); - when(mockWifiInfo.getCurrentNetworkKey()).thenReturn(TEST_WIFI_NETWORK_KEY); + when(mockWifiInfo.getNetworkKey()).thenReturn(TEST_WIFI_NETWORK_KEY); final LinkProperties prop = new LinkProperties(); prop.setInterfaceName(TEST_IFACE); final NetworkCapabilities networkCapabilities = new NetworkCapabilities.Builder() diff --git a/services/wallpapereffectsgeneration/OWNERS b/services/wallpapereffectsgeneration/OWNERS new file mode 100644 index 000000000000..d2d3e2c0a7b6 --- /dev/null +++ b/services/wallpapereffectsgeneration/OWNERS @@ -0,0 +1,4 @@ +susharon@google.com +shanh@google.com +huiwu@google.com +srazdan@google.com diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java index e59c2e41a6c0..9a764a0a0a3a 100644 --- a/telephony/java/android/telephony/CarrierConfigManager.java +++ b/telephony/java/android/telephony/CarrierConfigManager.java @@ -4883,6 +4883,10 @@ public class CarrierConfigManager { /** Specifies the PCO id for IPv4 Epdg server address */ public static final String KEY_EPDG_PCO_ID_IPV4_INT = KEY_PREFIX + "epdg_pco_id_ipv4_int"; + /** Controls if the IKE tunnel setup supports EAP-AKA fast reauth */ + public static final String KEY_SUPPORTS_EAP_AKA_FAST_REAUTH_BOOL = + KEY_PREFIX + "supports_eap_aka_fast_reauth_bool"; + /** @hide */ @IntDef({AUTHENTICATION_METHOD_EAP_ONLY, AUTHENTICATION_METHOD_CERT}) public @interface AuthenticationMethodType {} @@ -5029,6 +5033,7 @@ public class CarrierConfigManager { defaults.putBoolean(KEY_ADD_KE_TO_CHILD_SESSION_REKEY_BOOL, false); defaults.putInt(KEY_EPDG_PCO_ID_IPV6_INT, 0); defaults.putInt(KEY_EPDG_PCO_ID_IPV4_INT, 0); + defaults.putBoolean(KEY_SUPPORTS_EAP_AKA_FAST_REAUTH_BOOL, false); return defaults; } diff --git a/telephony/java/android/telephony/SubscriptionManager.java b/telephony/java/android/telephony/SubscriptionManager.java index f72832438204..4e32a55b2e6e 100644 --- a/telephony/java/android/telephony/SubscriptionManager.java +++ b/telephony/java/android/telephony/SubscriptionManager.java @@ -3820,6 +3820,11 @@ public class SubscriptionManager { * {@link #PHONE_NUMBER_SOURCE_UICC UICC} and decide if the previously set phone number * of source {@link #PHONE_NUMBER_SOURCE_CARRIER carrier} should be updated. * + * <p>The API provides no guarantees of what format the number is in: the format can vary + * depending on the {@code source} and the network etc. Programmatic parsing should be done + * cautiously, for example, after formatting the number to a consistent format with + * {@link android.telephony.PhoneNumberUtils#formatNumberToE164(String, String)}. + * * <p>Note the assumption is that one subscription (which usually means one SIM) has * only one phone number. The multiple sources backup each other so hopefully at least one * is availavle. For example, for a carrier that doesn't typically set phone numbers @@ -3878,6 +3883,11 @@ public class SubscriptionManager { * from available sources in the following order: {@link #PHONE_NUMBER_SOURCE_CARRIER} * > {@link #PHONE_NUMBER_SOURCE_UICC} > {@link #PHONE_NUMBER_SOURCE_IMS}. * + * <p>The API provides no guarantees of what format the number is in: the format can vary + * depending on the underlying source and the network etc. Programmatic parsing should be done + * cautiously, for example, after formatting the number to a consistent format with + * {@link android.telephony.PhoneNumberUtils#formatNumberToE164(String, String)}. + * * @param subscriptionId the subscription ID, or {@link #DEFAULT_SUBSCRIPTION_ID} * for the default one. * @return the phone number, or an empty string if not available. @@ -3916,6 +3926,9 @@ public class SubscriptionManager { * <p>The API is suitable for carrier apps to provide a phone number, for example when * it's not possible to update {@link #PHONE_NUMBER_SOURCE_UICC UICC} directly. * + * <p>It's recommended that the phone number is formatted to well-known formats, + * for example, by {@link PhoneNumberUtils} {@code formatNumber*} methods. + * * @param subscriptionId the subscription ID, or {@link #DEFAULT_SUBSCRIPTION_ID} * for the default one. * @param number the phone number, or an empty string to remove the previously set number. diff --git a/telephony/java/android/telephony/TelephonyManager.java b/telephony/java/android/telephony/TelephonyManager.java index 9ac9d66b3965..aab6daa20279 100644 --- a/telephony/java/android/telephony/TelephonyManager.java +++ b/telephony/java/android/telephony/TelephonyManager.java @@ -11487,7 +11487,11 @@ public class TelephonyManager { private final int mErrorCode; - /** @hide */ + /** + * An exception with ModemActivityInfo specific error codes. + * + * @param errorCode a ModemActivityInfoError code. + */ public ModemActivityInfoException(@ModemActivityInfoError int errorCode) { mErrorCode = errorCode; } diff --git a/telephony/java/android/telephony/ims/RcsUceAdapter.java b/telephony/java/android/telephony/ims/RcsUceAdapter.java index 61de3ac2b25e..154bb11db5e3 100644 --- a/telephony/java/android/telephony/ims/RcsUceAdapter.java +++ b/telephony/java/android/telephony/ims/RcsUceAdapter.java @@ -268,6 +268,13 @@ public class RcsUceAdapter { @SystemApi public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_NR5G_VOPS_ENABLED = 11; + /** + * A capability update has been requested due to IMS being registered over INTERNET PDN. + * @hide + */ + @SystemApi + public static final int CAPABILITY_UPDATE_TRIGGER_MOVE_TO_INTERNET_PDN = 12; + /**@hide*/ @Retention(RetentionPolicy.SOURCE) @IntDef(prefix = "ERROR_", value = { @@ -282,7 +289,8 @@ public class RcsUceAdapter { CAPABILITY_UPDATE_TRIGGER_MOVE_TO_WLAN, CAPABILITY_UPDATE_TRIGGER_MOVE_TO_IWLAN, CAPABILITY_UPDATE_TRIGGER_MOVE_TO_NR5G_VOPS_DISABLED, - CAPABILITY_UPDATE_TRIGGER_MOVE_TO_NR5G_VOPS_ENABLED + CAPABILITY_UPDATE_TRIGGER_MOVE_TO_NR5G_VOPS_ENABLED, + CAPABILITY_UPDATE_TRIGGER_MOVE_TO_INTERNET_PDN }) public @interface StackPublishTriggerType {} diff --git a/tests/FlickerTests/src/com/android/server/wm/flicker/close/OWNERS b/tests/FlickerTests/src/com/android/server/wm/flicker/close/OWNERS new file mode 100644 index 000000000000..f7c0a87f5dac --- /dev/null +++ b/tests/FlickerTests/src/com/android/server/wm/flicker/close/OWNERS @@ -0,0 +1,2 @@ +# window manager > animations/transitions +# Bug component: 316275 diff --git a/tests/FlickerTests/src/com/android/server/wm/flicker/ime/OWNERS b/tests/FlickerTests/src/com/android/server/wm/flicker/ime/OWNERS new file mode 100644 index 000000000000..301fafa5309e --- /dev/null +++ b/tests/FlickerTests/src/com/android/server/wm/flicker/ime/OWNERS @@ -0,0 +1,2 @@ +# ime +# Bug component: 34867 diff --git a/tests/FlickerTests/src/com/android/server/wm/flicker/launch/OWNERS b/tests/FlickerTests/src/com/android/server/wm/flicker/launch/OWNERS new file mode 100644 index 000000000000..2c414a27cacb --- /dev/null +++ b/tests/FlickerTests/src/com/android/server/wm/flicker/launch/OWNERS @@ -0,0 +1,4 @@ +# System UI > ... > Overview (recent apps) > UI +# Bug template url: https://b.corp.google.com/issues/new?component=807991&template=1390280 = per-file *Overview* +# window manager > animations/transitions +# Bug template url: https://b.corp.google.com/issues/new?component=316275&template=1018192 diff --git a/tests/FlickerTests/src/com/android/server/wm/flicker/quickswitch/OWNERS b/tests/FlickerTests/src/com/android/server/wm/flicker/quickswitch/OWNERS new file mode 100644 index 000000000000..897fe5dee7fb --- /dev/null +++ b/tests/FlickerTests/src/com/android/server/wm/flicker/quickswitch/OWNERS @@ -0,0 +1,2 @@ +# System UI > ... > Launcher > Gesture nav +# Bug component: 565144 diff --git a/tests/FlickerTests/src/com/android/server/wm/flicker/rotation/OWNERS b/tests/FlickerTests/src/com/android/server/wm/flicker/rotation/OWNERS new file mode 100644 index 000000000000..f7c0a87f5dac --- /dev/null +++ b/tests/FlickerTests/src/com/android/server/wm/flicker/rotation/OWNERS @@ -0,0 +1,2 @@ +# window manager > animations/transitions +# Bug component: 316275 |