blob: 203ab0a0c1a23e85e2c96ae897af0fef432b38c0 [file] [log] [blame]
/*
* Copyright (C) 2023 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.
*/
syntax = "proto2";
package android.os.statsd.cronet;
import "frameworks/proto_logging/stats/atoms.proto";
import "frameworks/proto_logging/stats/atom_field_options.proto";
option java_package = "com.android.os.cronet";
option java_multiple_files = true;
extend Atom {
optional CronetEngineCreated cronet_engine_created = 703
[(module) = "cronet"];
optional CronetTrafficReported cronet_traffic_reported = 704
[(module) = "cronet"];
optional CronetEngineBuilderInitialized cronet_engine_builder_initialized = 762 [(module) = "cronet"];
optional CronetHttpFlagsInitialized cronet_http_flags_initialized = 763 [(module) = "cronet"];
optional CronetInitialized cronet_initialized = 764 [(module) = "cronet"];
}
// Logged every time CronetEngine.Builder#build() returns.
message CronetEngineCreated {
// A weak-ID-like reference to the instance of the Cronet engine being
// created. The field can be used to join subsequent request metrics with the
// engine details.
//
// The reference is NOT meant to be globally (or even on-device) unique, but
// on device collisions should be unlikely.
// Defaults to max positive int64 value which is equivalent to "not set".
optional int64 engine_instance_ref = 1 [default = 9223372036854775807];
// Deprecated, moved to CronetEngineBuilderInitialized
optional int32 major_version = 2 [deprecated = true];
// Deprecated, moved to CronetEngineBuilderInitialized
optional int32 minor_version = 3 [deprecated = true];
// Deprecated, moved to CronetEngineBuilderInitialized
optional int32 build_version = 4 [deprecated = true];
// Deprecated, moved to CronetEngineBuilderInitialized
optional int32 patch_version = 5 [deprecated = true];
// Deprecated, moved to CronetInitialized
optional CronetSource source = 6 [deprecated = true];
// Options that can be set on the Cronet builder. Only fields which are
// actively set by the Cronet user are populated. When using the protos
// default values should be considered as "null" - default semnantics can
// change based on the Cronet version.
//
// Fields that can contain free text (even if just theoretically) should be
// curated and/or replaced with fields that provide useful signal while not
// being sensitive. For instance, instead of logging values of quic hint hosts
// verbatim, prefer to log if a request was affected by a hint.
//
// For field names, follow the nomenclature below:
// - fields set directly on the builder should have no prefix
// (e.g., enableBrotli() translates to enable_brotli)
// - fields which are set in a sub-object or sub-structure should be prefixed
// with the path leading to that field. For example,
// builder.setExperimentalOptions("quic: { foo: { bar: 2 } }");
// translates to experimental_options_quic_foo_bar
//
//
// In both cases, keep the existing names that are used in Cronet if at all
// possible.
// --- CronetEngine.Builder controls ---
optional bool enable_brotli = 7;
optional bool enable_http2 = 8;
optional CronetHttpCacheMode http_cache_mode = 9;
optional bool enable_public_key_pinning_bypass_for_local_trust_anchors = 10;
optional bool enable_quic = 11;
// --- ExperimentalCronetEngine.Builder controls ---
optional bool enable_network_quality_estimator = 12;
optional int32 thread_priority = 13;
// --- JSON experimental options ---
// The JSON config offers a lot of options but most of the atoms will have
// a majority of the fields below unset. We considered lumping the boolean
// flags into a single int32 field bud decided not to do so because
// a) having the standalone booleans makes the data set easier to understand
// and use
// b) we need to distinguish between three states (unset / true / false)
// which makes the compaction less efficient
// c) we expect the booleans to not be set in majority of the cases,
// in such a case, no space is saved.
// QUIC
// Lexicographically sorted, comma separated, curated list of QUIC connection
// options.
optional string experimental_options_quic_connection_options = 14;
optional OptionalBoolean
experimental_options_quic_store_server_configs_in_properties = 15;
// Unset value is -1
optional int32
experimental_options_quic_max_server_configs_stored_in_properties = 16
[default = -1];
// Unset value is -1
optional int32 experimental_options_quic_idle_connection_timeout_seconds = 17
[default = -1];
optional OptionalBoolean
experimental_options_quic_goaway_sessions_on_ip_change = 18;
optional OptionalBoolean
experimental_options_quic_close_sessions_on_ip_change = 19;
optional OptionalBoolean
experimental_options_quic_migrate_sessions_on_network_change_v2 = 20;
optional OptionalBoolean experimental_options_quic_migrate_sessions_early_v2 =
21;
optional OptionalBoolean
experimental_options_quic_quic_disable_bidirectional_streams = 22;
// Unset value is -1
optional int32
experimental_options_quic_max_time_before_crypto_handshake_seconds = 23
[default = -1];
// Unset value is -1
optional int32
experimental_options_quic_max_idle_time_before_crypto_handshake_seconds =
24 [default = -1];
optional OptionalBoolean
experimental_options_quic_enable_socket_recv_optimization = 25;
// DNS
optional OptionalBoolean experimental_options_asyncdns_enable = 26;
optional OptionalBoolean experimental_options_staledns_enable = 27;
// Unset value is -1
optional int32 experimental_options_staledns_delay_ms = 28 [default = -1];
// Unset value is -1
optional int32 experimental_options_staledns_max_expired_time_ms = 29
[default = -1];
// Unset value is -1
optional int32 experimental_options_staledns_max_stale_uses = 30
[default = -1];
optional OptionalBoolean experimental_options_staledns_allow_other_network =
31;
optional OptionalBoolean experimental_options_staledns_persist_to_disk = 32;
// Unset value is -1
optional int32 experimental_options_staledns_persist_delay_ms = 33
[default = -1];
optional OptionalBoolean
experimental_options_staledns_use_stale_on_name_not_resolved = 34;
// Host resolver rules omitted
optional OptionalBoolean experimental_options_disable_ipv6_on_wifi = 35;
// Deprecated, moved to CronetEngineBuilderInitialized.
enum CronetSource {
option deprecated = true;
// Safe default, don't use explicitly.
CRONET_SOURCE_UNSPECIFIED = 0;
// The library is bundled with the application.
CRONET_SOURCE_STATICALLY_LINKED = 1;
// The library is loaded from GMS Core
CRONET_SOURCE_GMSCORE_DYNAMITE = 2;
// The application is using the fallback implementation
CRONET_SOURCE_FALLBACK = 3;
}
// A pointer to CronetInitialized.cronet_initialization_ref for the Cronet initialization
// sequence that this engine relied on.
// Note that CronetInitialized may be logged after CronetEngineCreated because initialization
// continues in the background after the CronetEngine is instantiated.
// One consequence is that this reference can be broken if a
// crash occurs after the engine is created but before initialization is complete.
optional int64 cronet_initialization_ref = 36;
// See
// https://developer.android.com/guide/topics/connectivity/cronet/reference/org/chromium/net/CronetEngine.Builder.html#constants
// for detailed semantics.
enum CronetHttpCacheMode {
// Safe default, don't use explicitly.
HTTP_CACHE_MODE_UNSPECIFIED = 0;
HTTP_CACHE_DISABLED = 1;
HTTP_CACHE_DISK = 2;
HTTP_CACHE_DISK_NO_HTTP = 3;
HTTP_CACHE_IN_MEMORY = 4;
}
}
// Logged when a request has reached terminal state after the final user callback has returned
// and before the requestFinishedListeners has fired.
message CronetTrafficReported {
// The Cronet engine that sent the trafic. See
// CronetEngineCreated.engine_instance_ref for more details.
// Defaults to max negative int64 value which is equivalent to "not set".
// The default value is deliberately different from
// CronetEngineCreated.engine_instance_ref to avoid unintentional joining.
optional int64 engine_instance_ref = 1 [default = -9223372036854775808];
// Bucketized sizes for request and response headers and body.
optional CronetRequestHeadersSizeBucket request_headers_size = 2;
optional CronetRequestBodySizeBucket request_body_size = 3;
optional CronetResponseHeadersSizeBucket response_headers_size = 4;
optional CronetResponseBodySizeBucket response_body_size = 5;
// The status code of the response.
optional int32 http_status_code = 6;
// The Fingerprint2011 hash of the protocol that was negotiated for this
// request (as returned by UrlResponseInfo.getNegotiatedProtocol()). The
// possible values for the string are limited so the hash is sufficient
// to identify known values while preventing accidental presence of
// freeform text.
// See go/cronet-negotiated-protocols for possible values.
optional int64 negotiated_protocol_hash = 7;
// The time it took from starting the request to receiving the full set of
// response headers, in milliseconds.
optional int32 headers_latency_millis = 8;
// The time that elapsed from the point UrlRequest#start() was called to the point
// we are ready to call the final user callback (e.g. onSucceeded).
// Note: this includes time spent waiting for the user to issue an I/O request.
// In other words this includes the effect of the user
// throttling Cronet (a.k.a. flow control, a.k.a. backpressure).
// See also total_idle_time_millis
optional int32 overall_latency_millis = 9;
// Whether a connection migration was attempted for this request.
optional bool connection_migration_attempted = 10;
// Whether a connection migration was attempted and successful for this
// request.
optional bool connection_migration_successful = 11;
// Number of previous CronetTrafficReported records that were dropped due to rate limiting.
optional int32 samples_rate_limited = 12;
// Terminal state of the reported request.
optional CronetRequestTerminalState terminal_state = 13;
enum CronetRequestTerminalState {
STATE_UNKNOWN = 0;
STATE_SUCCEEDED = 1;
STATE_ERROR = 2;
STATE_CANCELLED = 3;
}
// count of exceptions thrown during the execution of a user callback.
optional int32 user_callback_exception_count = 14;
// Same as `overall_latency_millis`, but only including time spent with no
// outstanding I/O request from the user. For example, the time that elapses between Cronet
// becoming ready to call the onReadCompleted callback and the user making the
// next UrlRequest#read() call is idle time: during that time
// there is no outstanding read request.
// If this value is large relative to overall_latency_millis, it may mean the request was
// throttled by the user, i.e. they applied backpressure/flow control, intentionally or not.
// Note that in this context, "idle" should be interpreted from the
// perspective of the Cronet user. Internally, Cronet might not actually be "idle"
// as it may still attempt to keep its internal buffers filled.
// An example of Cronet idly waiting for the user would look like the following
/*
Cronet User
|
|
|----- OnResponseStarted ------|
|
Cronet |
Idle |
Time |
|
Cronet |------------------------------| User calls request.read()
Doing |
Work |
|
OnReadCompleted |
|
|----- onReadCompleted -------|
| Cronet Idle Time includes the time taken to call
| Executor#execute() on the user's executor.
|
Cronet | If the user is blocking the network
Idle | thread in Executor#execute(), then technically that
Time | counts as backpressure / flow control.
|
|
|
|
|
|
|
|
|
|
|------------------------------|
*/
// This field contains the sum of Cronet Idle time waiting for user calls.
optional int64 total_idle_time_millis = 15;
// The time it takes for the user's Executor#execute() method to return
// Note: contrary to most other metrics in this atom, this also includes
// the final user callback (e.g. onSucceeded).
// Note: in the case of the native implementation, Executor#execute() is called on
// the network thread, which is a shared resource. High values for this metric are
// usually a red flag because they mean the network thread is unable to service any
// other UrlRequests during this time (including those from other engines).
optional int64 total_user_executor_execute_latency_millis = 16;
// The total amount of times `UrlRequest#read()` was called.
optional int32 read_count = 17;
// The total amount of times `UploadDataProvider#read` has been fired.
optional int32 on_upload_read_count = 18;
// Indicates if the request is a bidirectional stream or not.
optional OptionalBoolean is_bidi_stream = 19;
enum CronetRequestHeadersSizeBucket {
REQUEST_HEADERS_SIZE_BUCKET_UNSPECIFIED = 0;
// It's impossible to send requests without any headers in Cronet
REQUEST_HEADERS_SIZE_BUCKET_UNDER_ONE_KIB = 1;
REQUEST_HEADERS_SIZE_BUCKET_ONE_TO_TEN_KIB = 2;
REQUEST_HEADERS_SIZE_BUCKET_TEN_TO_TWENTY_FIVE_KIB = 3;
REQUEST_HEADERS_SIZE_BUCKET_TWENTY_FIVE_TO_FIFTY_KIB = 4;
REQUEST_HEADERS_SIZE_BUCKET_FIFTY_TO_HUNDRED_KIB = 5;
REQUEST_HEADERS_SIZE_BUCKET_OVER_HUNDRED_KIB = 6;
}
enum CronetRequestBodySizeBucket {
REQUEST_BODY_SIZE_BUCKET_UNSPECIFIED = 0;
REQUEST_BODY_SIZE_BUCKET_ZERO = 1;
REQUEST_BODY_SIZE_BUCKET_UNDER_TEN_KIB = 2;
REQUEST_BODY_SIZE_BUCKET_TEN_TO_FIFTY_KIB = 3;
REQUEST_BODY_SIZE_BUCKET_FIFTY_TO_TWO_HUNDRED_KIB = 4;
REQUEST_BODY_SIZE_BUCKET_TWO_HUNDRED_TO_FIVE_HUNDRED_KIB = 5;
REQUEST_BODY_SIZE_BUCKET_FIVE_HUNDRED_KIB_TO_ONE_MIB = 6;
REQUEST_BODY_SIZE_BUCKET_ONE_TO_FIVE_MIB = 7;
REQUEST_BODY_SIZE_BUCKET_OVER_FIVE_MIB = 8;
}
enum CronetResponseHeadersSizeBucket {
RESPONSE_HEADERS_SIZE_BUCKET_UNSPECIFIED = 0;
RESPONSE_HEADERS_SIZE_BUCKET_UNDER_ONE_KIB = 1;
RESPONSE_HEADERS_SIZE_BUCKET_ONE_TO_TEN_KIB = 2;
RESPONSE_HEADERS_SIZE_BUCKET_TEN_TO_TWENTY_FIVE_KIB = 3;
RESPONSE_HEADERS_SIZE_BUCKET_TWENTY_FIVE_TO_FIFTY_KIB = 4;
RESPONSE_HEADERS_SIZE_BUCKET_FIFTY_TO_HUNDRED_KIB = 5;
RESPONSE_HEADERS_SIZE_BUCKET_OVER_HUNDRED_KIB = 6;
}
enum CronetResponseBodySizeBucket {
RESPONSE_BODY_SIZE_BUCKET_UNSPECIFIED = 0;
RESPONSE_BODY_SIZE_BUCKET_ZERO = 1;
RESPONSE_BODY_SIZE_BUCKET_UNDER_TEN_KIB = 2;
RESPONSE_BODY_SIZE_BUCKET_TEN_TO_FIFTY_KIB = 3;
RESPONSE_BODY_SIZE_BUCKET_FIFTY_TO_TWO_HUNDRED_KIB = 4;
RESPONSE_BODY_SIZE_BUCKET_TWO_HUNDRED_TO_FIVE_HUNDRED_KIB = 5;
RESPONSE_BODY_SIZE_BUCKET_FIVE_HUNDRED_KIB_TO_ONE_MIB = 6;
RESPONSE_BODY_SIZE_BUCKET_ONE_TO_FIVE_MIB = 7;
RESPONSE_BODY_SIZE_BUCKET_OVER_FIVE_MIB = 8;
}
}
// Logged when the HTTP flags have been read.
message CronetHttpFlagsInitialized {
// A weak-ID-like reference to the http flags loading operation.
// The field can be used to join with CronetEngineBuilderInitialized atom.
optional int64 cronet_http_flags_ref = 1;
// how long it took to load (or attempt to load) http flags.
// This field is set to -1 if flag loading was not attempted
// (e.g. because the app opted out of Cronet flag support).
// Note: There is no support for unset values, hence -1 is used.
optional int32 http_flags_latency_millis = 2 [default = -1];
// Determine whether flag loading was successful or not.
optional OptionalBoolean flags_successful = 3;
// The first 8 bytes of the MD5 hashes, interpreted as signed little-endian integers,
// of the HTTP flag names that the Cronet instance logging the atoms is
// actually running with.
repeated int64 http_flags_names = 4 [packed = true];
// The effective values of the flags, in the same order as
// http_flags_names.
// For boolean flags, this is 0 or 1.
// For integer flags, this is the value of the flag itself.
// For float values, this is the floating point value multiplied by 1 billion,
// rounded, and clamped to the int64 range. (This should result in distinct
// values for most commonly used floating point inputs.)
// For string or bytes flags, this is a hash of the value
// calculated in the same way as http_flags_names above.
repeated int64 http_flags_values = 5 [packed = true];
}
/*
--------------------- -----------------
| | createBuilder() | | ================⦀
| Provider | -------------------------------> | Builder | ⦀
| | | | ⦀
|-------------------| engine_builder_created_lat |---------------- ⦀
| ⦀
Build() | engine_created_latency ⦀
| ⦀
V ⦀
------------------ ------------------- ⦀
| | | | ⦀
| REQ CAN START | <------------- | Engine | ⦀
|WITHOUT BLOCKING| | | ⦀
|----------------| |-----------------| ⦀
⦀ ⦀
==================================================================⦀
engine_async_latency (This takes a variable amount of time depending on async jobs)
engine_builder_created_latency: The wall time elapsed since createBuilder() has been called
until a builder has been returned.
engine_created_latency: The wall time elapsed since Build() has been called until a CronetEngine
has been returned.
engine_async_latency: The wall time elapsed since Build()
has been called until the returned CronetEngine
is usable (All Asynchronous setup calls have finished executing).
*/
// Logged once for each CronetSource when createBuilder() has returned.
// This atom should normally be logged from Cronet API code (as opposed to impl code).
// If the app is bundling a Cronet API version that is too old to know about this atom,
// the impl takes responsibility for logging this atom and attempts to do so soon as
// the impl is loaded. Some fields may be missing in this case.
message CronetEngineBuilderInitialized {
// A weak-ID-like reference to the instance of the Cronet initialization.
// The field can be used to join subsequent engine creation and request
// metrics with the initialization details.
optional int64 cronet_initialization_ref = 1;
// How long it took to produce the first `CronetEngine.Builder` instance for the source specified.
// This field can be set by Api layer or Impl Layer, If this field was set by the Impl layer then
// the value of the field will be equal to -1.
optional int32 engine_builder_created_latency_millis = 2 [default = -1];
// Source of the Cronet being loaded
optional Source source = 3;
enum Source {
// Safe default, don't use explicitly.
CRONET_SOURCE_UNSPECIFIED = 0;
// Native-based Cronet implementation, bundled within the client app.
CRONET_SOURCE_EMBEDDED_NATIVE = 1;
// Java-based Cronet implementation, bundled within the client app.
CRONET_SOURCE_EMBEDDED_JAVA = 2;
// Native-based Cronet implementation, loaded from GMS Core (Google Play Services).
CRONET_SOURCE_GMSCORE_NATIVE = 3;
// Native-based Cronet implementation, loaded from the bootclasspath
// through the android.net.http.HttpEngine API.
CRONET_SOURCE_HTTPENGINE_NATIVE = 4;
}
// Whether the Provider successfully created a builder or not.
// This field can be set by Api layer or Impl Layer, If this field was set by the Impl layer then
// the value of the field will be equal to `UNSET`.
optional OptionalBoolean creation_successful = 4;
// A weak-ID-like reference to the http flags loading operation.
// The field can be used to join with CronetHttpFlagsInitialized atoms.
// Note: at the time of writing, loading of flags happens after the builder creation
// has returned. This means the corresponding CronetHttpFlagsLoaded is logged
// after or might not be logged at all (if there was a crash or
// the resulting builder was never used).
optional int64 cronet_http_flags_ref = 5;
// This field carries the value stored in the file below
// https://source.chromium.org/chromium/chromium/src/+/main:components/cronet/android/api/src/org/chromium/net/ApiVersion.template
optional int32 cronet_api_level = 6;
// This field carries the value stored in the file below
// https://source.chromium.org/chromium/chromium/src/+/main:components/cronet/android/java/src/org/chromium/net/impl/ImplVersion.template
optional int32 cronet_impl_api_level = 7;
// The following fields corresponds to the version of Chromium for which the implementation
// was compiled against as seen https://source.chromium.org/chromium/chromium/src/+/main:chrome/VERSION;l=1;bpv=0;bpt=0
optional int32 major_version = 8;
optional int32 minor_version = 9;
optional int32 build_version = 10;
optional int32 patch_version = 11;
// The Android UID of the process that Cronet was initialized in.
optional int32 uid = 12 [(is_uid) = true];
}
// Logged once for each CronetSource when the first CronetEngine is ready to be used.
// Note that CronetInitialized may be logged after CronetEngineCreated because initialization
// may continue in the background after the CronetEngine is instantiated.
// One consequence is that cronet_initialization_ref can be broken if a
// crash occurs after the engine is created but before initialization is complete.
message CronetInitialized {
// A weak-ID-like reference to the instance of the Cronet initialization.
// The field can be used to join subsequent engine creation and request
// metrics with the native details.
optional int64 cronet_initialization_ref = 1;
// The wall clock time spent in the execution of the first call to `CronetEngine.Builder#build`
optional int32 engine_creation_latency_millis = 2 [default = -1];
// How much wall clock time was spent from the moment the first `CronetEngine.Builder#build()`
// was made and the point where Cronet is ready to send requests. Notably,
// this includes the time it took for any asynchronous background initialization code to complete
optional int32 engine_async_latency_millis = 3 [default = -1];
}
// Distinguishes between three states (unset / true / false)
enum OptionalBoolean {
UNSET = 0;
TRUE = 1;
FALSE = 2;
}