diff --git a/.gitignore b/.gitignore index 1b1b040dc59..559640744f2 100644 --- a/.gitignore +++ b/.gitignore @@ -41,6 +41,7 @@ /vendor/python_26/ /vendor/native_mksnapshot /vendor/LICENSES.chromium.html +/vendor/pyyaml node_modules/ SHASUMS256.txt **/yarn.lock diff --git a/DEPS b/DEPS index d678ffd4472..029e9db0394 100644 --- a/DEPS +++ b/DEPS @@ -1,17 +1,21 @@ vars = { 'chromium_version': '67.0.3396.99', - 'libchromiumcontent_revision': - '5db6529f9663a48ee3e6f4265a6abe7806f1dfbf', 'node_version': '9dcbed23f016d3ad081be6ec7fb5122e57862da7', + 'pyyaml_version': + '3.12', + 'chromium_git': 'https://chromium.googlesource.com', 'electron_git': 'https://github.com/electron', + 'yaml_git': + 'https://github.com/yaml', + 'checkout_nacl': False, 'checkout_libaom': @@ -23,22 +27,22 @@ vars = { deps = { 'src': (Var("chromium_git")) + '/chromium/src.git@' + (Var("chromium_version")), - 'src/libchromiumcontent': - (Var("electron_git")) + '/libchromiumcontent.git@' + (Var("libchromiumcontent_revision")), 'src/third_party/electron_node': (Var("electron_git")) + '/node.git@' + (Var("node_version")), + 'src/electron/vendor/pyyaml': + (Var("yaml_git")) + '/pyyaml.git@' + (Var("pyyaml_version")), } hooks = [ { 'action': [ 'python', - 'src/libchromiumcontent/script/apply-patches', + 'src/electron/script/apply-patches', '--project-root=.', '--commit' ], 'pattern': - 'src/libchromiumcontent', + 'src/electron', 'name': 'patch_chromium' }, diff --git a/build/config/BUILD.gn b/build/config/BUILD.gn new file mode 100644 index 00000000000..677ac8b8fa8 --- /dev/null +++ b/build/config/BUILD.gn @@ -0,0 +1,25 @@ +config("build_time_executable") { + configs = [] + + if (is_electron_build && !is_component_build) { + # The executables which have this config applied are dependent on ffmpeg, + # which is always a shared library in an Electron build. However, in the + # non-component build, executables don't have rpath set to search for + # libraries in the executable's directory, so ffmpeg cannot be found. So + # let's make sure rpath is set here. + # See '//build/config/gcc/BUILD.gn' for details on the rpath setting. + if (is_linux) { + configs += [ "//build/config/gcc:rpath_for_built_shared_libraries" ] + } + + if (is_mac) { + ldflags = [ "-Wl,-rpath,@loader_path/." ] + } + } +} +# For MAS build, we force defining "MAS_BUILD". +config("mas_build") { + if (is_mas_build) { + defines = [ "MAS_BUILD" ] + } +} diff --git a/patches/common/angle/.patches.yaml b/patches/common/angle/.patches.yaml new file mode 100644 index 00000000000..fe64e3cb195 --- /dev/null +++ b/patches/common/angle/.patches.yaml @@ -0,0 +1,6 @@ +repo: src/third_party/angle +patches: +- + author: Ales Pergl + file: dcheck.patch + description: null diff --git a/patches/common/angle/dcheck.patch b/patches/common/angle/dcheck.patch new file mode 100644 index 00000000000..05114b59739 --- /dev/null +++ b/patches/common/angle/dcheck.patch @@ -0,0 +1,13 @@ +diff --git a/src/common/debug.h b/src/common/debug.h +index 0108ff655..57fbc5ac5 100644 +--- a/src/common/debug.h ++++ b/src/common/debug.h +@@ -190,7 +190,7 @@ std::ostream &FmtHexInt(std::ostream &os, T value) + + #define ANGLE_EMPTY_STATEMENT for (;;) break + #if !defined(NDEBUG) || defined(ANGLE_ENABLE_RELEASE_ASSERTS) +-#define ANGLE_ENABLE_ASSERTS ++// #define ANGLE_ENABLE_ASSERTS + #endif + + #define WARN() ANGLE_LOG(WARN) diff --git a/patches/common/boringssl/.patches.yaml b/patches/common/boringssl/.patches.yaml new file mode 100644 index 00000000000..33621e43c7c --- /dev/null +++ b/patches/common/boringssl/.patches.yaml @@ -0,0 +1,12 @@ +repo: src/third_party/boringssl/src +patches: +- + author: Jeremy Apthorp + file: 0001-Implement-legacy-OCSP-APIs-for-libssl.patch + description: see patch header +- + author: Aleksei Kuzmin + file: implement-SSL_get_tlsext_status_type.patch + description: | + BoringSSL doesn't implement `SSL_get_tlsext_status_type()`, + but Node.js expects it to be present cause OpenSSL has it. diff --git a/patches/common/boringssl/0001-Implement-legacy-OCSP-APIs-for-libssl.patch b/patches/common/boringssl/0001-Implement-legacy-OCSP-APIs-for-libssl.patch new file mode 100644 index 00000000000..d1c0c0d2071 --- /dev/null +++ b/patches/common/boringssl/0001-Implement-legacy-OCSP-APIs-for-libssl.patch @@ -0,0 +1,741 @@ +From 81d4909d00c3628453a8712bc331304bd01d8eaf Mon Sep 17 00:00:00 2001 +From: David Benjamin +Date: Thu, 10 May 2018 19:55:02 -0400 +Subject: [PATCH] Implement legacy OCSP APIs for libssl. + +Previously, we'd omitted OpenSSL's OCSP APIs because they depend on a +complex OCSP mechanism and encourage the the unreliable server behavior +that hampers using OCSP stapling to fix revocation today. (OCSP +responses should not be fetched on-demand on a callback. They should be +managed like other server credentials and refreshed eagerly, so +temporary CA outage does not translate to loss of OCSP.) + +But most of the APIs are byte-oriented anyway, so they're easy to +support. Intentionally omit the one that takes a bunch of OCSP_RESPIDs. + +The callback is benign on the client (an artifact of OpenSSL reading +OCSP and verifying certificates in the wrong order). On the server, it +encourages unreliability, but pyOpenSSL/cryptography.io depends on this. +Dcument that this is only for compatibility with legacy software. + +Also tweak a few things for compatilibility. cryptography.io expects +SSL_CTX_set_read_ahead to return something, SSL_get_server_tmp_key's +signature was wrong, and cryptography.io tries to redefine +SSL_get_server_tmp_key if SSL_CTRL_GET_SERVER_TMP_KEY is missing. + +Change-Id: I2f99711783456bfb7324e9ad972510be8a95e845 +Reviewed-on: https://boringssl-review.googlesource.com/28404 +Commit-Queue: David Benjamin +CQ-Verified: CQ bot account: commit-bot@chromium.org +Reviewed-by: Adam Langley +--- + crypto/err/ssl.errordata | 1 + + include/openssl/ssl.h | 64 +++++++++++++-- + include/openssl/tls1.h | 1 + + ssl/handshake.cc | 16 ++++ + ssl/handshake_server.cc | 16 ++++ + ssl/internal.h | 5 ++ + ssl/ssl_lib.cc | 39 ++++++++- + ssl/test/bssl_shim.cc | 26 ++++++ + ssl/test/runner/alert.go | 122 +++++++++++++-------------- + ssl/test/runner/runner.go | 205 ++++++++++++++++++++++++++++++++++------------ + ssl/test/test_config.cc | 4 + + ssl/test/test_config.h | 4 + + 12 files changed, 381 insertions(+), 122 deletions(-) + +diff --git a/crypto/err/ssl.errordata b/crypto/err/ssl.errordata +index 7b63bc8..375df9a 100644 +--- a/crypto/err/ssl.errordata ++++ b/crypto/err/ssl.errordata +@@ -108,6 +108,7 @@ SSL,266,NO_SHARED_GROUP + SSL,280,NO_SUPPORTED_VERSIONS_ENABLED + SSL,185,NULL_SSL_CTX + SSL,186,NULL_SSL_METHOD_PASSED ++SSL,289,OCSP_CB_ERROR + SSL,187,OLD_SESSION_CIPHER_NOT_RETURNED + SSL,268,OLD_SESSION_PRF_HASH_MISMATCH + SSL,188,OLD_SESSION_VERSION_NOT_RETURNED +diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h +index 35506f7..d46a5af 100644 +--- a/include/openssl/ssl.h ++++ b/include/openssl/ssl.h +@@ -3715,14 +3715,14 @@ OPENSSL_EXPORT int SSL_set_tmp_rsa(SSL *ssl, const RSA *rsa); + // SSL_CTX_get_read_ahead returns zero. + OPENSSL_EXPORT int SSL_CTX_get_read_ahead(const SSL_CTX *ctx); + +-// SSL_CTX_set_read_ahead does nothing. +-OPENSSL_EXPORT void SSL_CTX_set_read_ahead(SSL_CTX *ctx, int yes); ++// SSL_CTX_set_read_ahead returns one. ++OPENSSL_EXPORT int SSL_CTX_set_read_ahead(SSL_CTX *ctx, int yes); + + // SSL_get_read_ahead returns zero. + OPENSSL_EXPORT int SSL_get_read_ahead(const SSL *ssl); + +-// SSL_set_read_ahead does nothing. +-OPENSSL_EXPORT void SSL_set_read_ahead(SSL *ssl, int yes); ++// SSL_set_read_ahead returns one. ++OPENSSL_EXPORT int SSL_set_read_ahead(SSL *ssl, int yes); + + // SSL_renegotiate put an error on the error queue and returns zero. + OPENSSL_EXPORT int SSL_renegotiate(SSL *ssl); +@@ -3793,7 +3793,7 @@ OPENSSL_EXPORT const COMP_METHOD *SSL_get_current_compression(SSL *ssl); + OPENSSL_EXPORT const COMP_METHOD *SSL_get_current_expansion(SSL *ssl); + + // SSL_get_server_tmp_key returns zero. +-OPENSSL_EXPORT int *SSL_get_server_tmp_key(SSL *ssl, EVP_PKEY **out_key); ++OPENSSL_EXPORT int SSL_get_server_tmp_key(SSL *ssl, EVP_PKEY **out_key); + + // SSL_CTX_set_tmp_dh returns 1. + OPENSSL_EXPORT int SSL_CTX_set_tmp_dh(SSL_CTX *ctx, const DH *dh); +@@ -4108,6 +4108,58 @@ extern "C++" OPENSSL_EXPORT void SSL_CTX_sess_set_get_cb( + int id_len, int *out_copy)); + #endif + ++// SSL_set_tlsext_status_type configures a client to request OCSP stapling if ++// |type| is |TLSEXT_STATUSTYPE_ocsp| and disables it otherwise. It returns one ++// on success and zero if handshake configuration has already been shed. ++// ++// Use |SSL_enable_ocsp_stapling| instead. ++OPENSSL_EXPORT int SSL_set_tlsext_status_type(SSL *ssl, int type); ++ ++// SSL_set_tlsext_status_ocsp_resp sets the OCSP response. It returns one on ++// success and zero on error. On success, |ssl| takes ownership of |resp|, which ++// must have been allocated by |OPENSSL_malloc|. ++// ++// Use |SSL_set_ocsp_response| instead. ++OPENSSL_EXPORT int SSL_set_tlsext_status_ocsp_resp(SSL *ssl, uint8_t *resp, ++ size_t resp_len); ++ ++// SSL_get_tlsext_status_ocsp_resp sets |*out| to point to the OCSP response ++// from the server. It returns the length of the response. If there was no ++// response, it sets |*out| to NULL and returns zero. ++// ++// Use |SSL_get0_ocsp_response| instead. ++// ++// WARNING: the returned data is not guaranteed to be well formed. ++OPENSSL_EXPORT size_t SSL_get_tlsext_status_ocsp_resp(const SSL *ssl, ++ const uint8_t **out); ++ ++// SSL_CTX_set_tlsext_status_cb configures the legacy OpenSSL OCSP callback and ++// returns one. Though the type signature is the same, this callback has ++// different behavior for client and server connections: ++// ++// For clients, the callback is called after certificate verification. It should ++// return one for success, zero for a bad OCSP response, and a negative number ++// for internal error. Instead, handle this as part of certificate verification. ++// (Historically, OpenSSL verified certificates just before parsing stapled OCSP ++// responses, but BoringSSL fixes this ordering. All server credentials are ++// available during verification.) ++// ++// Do not use this callback as a server. It is provided for compatibility ++// purposes only. For servers, it is called to configure server credentials. It ++// should return |SSL_TLSEXT_ERR_OK| on success, |SSL_TLSEXT_ERR_NOACK| to ++// ignore OCSP requests, or |SSL_TLSEXT_ERR_ALERT_FATAL| on error. It is usually ++// used to fetch OCSP responses on demand, which is not ideal. Instead, treat ++// OCSP responses like other server credentials, such as certificates or SCT ++// lists. Configure, store, and refresh them eagerly. This avoids downtime if ++// the CA's OCSP responder is briefly offline. ++OPENSSL_EXPORT int SSL_CTX_set_tlsext_status_cb(SSL_CTX *ctx, ++ int (*callback)(SSL *ssl, ++ void *arg)); ++ ++// SSL_CTX_set_tlsext_status_arg sets additional data for ++// |SSL_CTX_set_tlsext_status_cb|'s callback and returns one. ++OPENSSL_EXPORT int SSL_CTX_set_tlsext_status_arg(SSL_CTX *ctx, void *arg); ++ + + // Private structures. + // +@@ -4285,6 +4337,7 @@ struct ssl_session_st { + #define SSL_CTRL_GET_NUM_RENEGOTIATIONS doesnt_exist + #define SSL_CTRL_GET_READ_AHEAD doesnt_exist + #define SSL_CTRL_GET_RI_SUPPORT doesnt_exist ++#define SSL_CTRL_GET_SERVER_TMP_KEY doesnt_exist + #define SSL_CTRL_GET_SESSION_REUSED doesnt_exist + #define SSL_CTRL_GET_SESS_CACHE_MODE doesnt_exist + #define SSL_CTRL_GET_SESS_CACHE_SIZE doesnt_exist +@@ -4698,6 +4751,7 @@ OPENSSL_EXPORT bool SSL_apply_handback(SSL *ssl, Span handback); + #define SSL_R_NEGOTIATED_TB_WITHOUT_EMS_OR_RI 285 + #define SSL_R_SERVER_ECHOED_INVALID_SESSION_ID 286 + #define SSL_R_PRIVATE_KEY_OPERATION_FAILED 287 ++#define SSL_R_OCSP_CB_ERROR 289 + #define SSL_R_SSLV3_ALERT_CLOSE_NOTIFY 1000 + #define SSL_R_SSLV3_ALERT_UNEXPECTED_MESSAGE 1010 + #define SSL_R_SSLV3_ALERT_BAD_RECORD_MAC 1020 +diff --git a/include/openssl/tls1.h b/include/openssl/tls1.h +index 3424f3d..7a05969 100644 +--- a/include/openssl/tls1.h ++++ b/include/openssl/tls1.h +@@ -237,6 +237,7 @@ extern "C" { + #define TLSEXT_TYPE_dummy_pq_padding 54537 + + // status request value from RFC 3546 ++#define TLSEXT_STATUSTYPE_nothing (-1) + #define TLSEXT_STATUSTYPE_ocsp 1 + + // ECPointFormat values from RFC 4492 +diff --git a/ssl/handshake.cc b/ssl/handshake.cc +index 6432424..0a90b9f 100644 +--- a/ssl/handshake.cc ++++ b/ssl/handshake.cc +@@ -356,6 +356,22 @@ enum ssl_verify_result_t ssl_verify_peer_cert(SSL_HANDSHAKE *hs) { + ssl_send_alert(ssl, SSL3_AL_FATAL, alert); + } + ++ // Emulate OpenSSL's client OCSP callback. OpenSSL verifies certificates ++ // before it receives the OCSP, so it needs a second callback for OCSP. ++ if (ret == ssl_verify_ok && !ssl->server && ++ hs->new_session->ocsp_response != nullptr && ++ ssl->ctx->legacy_ocsp_callback != nullptr) { ++ int cb_ret = ++ ssl->ctx->legacy_ocsp_callback(ssl, ssl->ctx->legacy_ocsp_callback_arg); ++ if (cb_ret <= 0) { ++ OPENSSL_PUT_ERROR(SSL, SSL_R_OCSP_CB_ERROR); ++ ssl_send_alert(ssl, SSL3_AL_FATAL, ++ cb_ret == 0 ? SSL_AD_BAD_CERTIFICATE_STATUS_RESPONSE ++ : SSL_AD_INTERNAL_ERROR); ++ ret = ssl_verify_invalid; ++ } ++ } ++ + return ret; + } + +diff --git a/ssl/handshake_server.cc b/ssl/handshake_server.cc +index fa8a241..7a96767 100644 +--- a/ssl/handshake_server.cc ++++ b/ssl/handshake_server.cc +@@ -534,6 +534,22 @@ static enum ssl_hs_wait_t do_select_certificate(SSL_HANDSHAKE *hs) { + return ssl_hs_error; + } + ++ if (hs->ocsp_stapling_requested && ++ ssl->ctx->legacy_ocsp_callback != nullptr) { ++ switch (ssl->ctx->legacy_ocsp_callback( ++ ssl, ssl->ctx->legacy_ocsp_callback_arg)) { ++ case SSL_TLSEXT_ERR_OK: ++ break; ++ case SSL_TLSEXT_ERR_NOACK: ++ hs->ocsp_stapling_requested = false; ++ break; ++ default: ++ OPENSSL_PUT_ERROR(SSL, SSL_R_OCSP_CB_ERROR); ++ ssl_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_INTERNAL_ERROR); ++ return ssl_hs_error; ++ } ++ } ++ + if (ssl_protocol_version(ssl) >= TLS1_3_VERSION) { + // Jump to the TLS 1.3 state machine. + hs->state = state_tls13; +diff --git a/ssl/internal.h b/ssl/internal.h +index d13d5f2..1cdfb8e 100644 +--- a/ssl/internal.h ++++ b/ssl/internal.h +@@ -2140,6 +2140,11 @@ struct SSLContext { + // session tickets. + const SSL_TICKET_AEAD_METHOD *ticket_aead_method; + ++ // legacy_ocsp_callback implements an OCSP-related callback for OpenSSL ++ // compatibility. ++ int (*legacy_ocsp_callback)(SSL *ssl, void *arg); ++ void *legacy_ocsp_callback_arg; ++ + // verify_sigalgs, if not empty, is the set of signature algorithms + // accepted from the peer in decreasing order of preference. + uint16_t *verify_sigalgs; +diff --git a/ssl/ssl_lib.cc b/ssl/ssl_lib.cc +index 9f56d54..50608e9 100644 +--- a/ssl/ssl_lib.cc ++++ b/ssl/ssl_lib.cc +@@ -1591,9 +1591,9 @@ int SSL_CTX_get_read_ahead(const SSL_CTX *ctx) { return 0; } + + int SSL_get_read_ahead(const SSL *ssl) { return 0; } + +-void SSL_CTX_set_read_ahead(SSL_CTX *ctx, int yes) { } ++int SSL_CTX_set_read_ahead(SSL_CTX *ctx, int yes) { return 1; } + +-void SSL_set_read_ahead(SSL *ssl, int yes) { } ++int SSL_set_read_ahead(SSL *ssl, int yes) { return 1; } + + int SSL_pending(const SSL *ssl) { + return static_cast(ssl->s3->pending_app_data.size()); +@@ -2205,7 +2205,7 @@ const COMP_METHOD *SSL_get_current_compression(SSL *ssl) { return NULL; } + + const COMP_METHOD *SSL_get_current_expansion(SSL *ssl) { return NULL; } + +-int *SSL_get_server_tmp_key(SSL *ssl, EVP_PKEY **out_key) { return 0; } ++int SSL_get_server_tmp_key(SSL *ssl, EVP_PKEY **out_key) { return 0; } + + void SSL_CTX_set_quiet_shutdown(SSL_CTX *ctx, int mode) { + ctx->quiet_shutdown = (mode != 0); +@@ -2717,3 +2717,33 @@ void SSL_CTX_set_ticket_aead_method(SSL_CTX *ctx, + const SSL_TICKET_AEAD_METHOD *aead_method) { + ctx->ticket_aead_method = aead_method; + } ++ ++int SSL_set_tlsext_status_type(SSL *ssl, int type) { ++ ssl->ocsp_stapling_enabled = type == TLSEXT_STATUSTYPE_ocsp; ++ return 1; ++} ++ ++int SSL_set_tlsext_status_ocsp_resp(SSL *ssl, uint8_t *resp, size_t resp_len) { ++ if (SSL_set_ocsp_response(ssl, resp, resp_len)) { ++ OPENSSL_free(resp); ++ return 1; ++ } ++ return 0; ++} ++ ++size_t SSL_get_tlsext_status_ocsp_resp(const SSL *ssl, const uint8_t **out) { ++ size_t ret; ++ SSL_get0_ocsp_response(ssl, out, &ret); ++ return ret; ++} ++ ++int SSL_CTX_set_tlsext_status_cb(SSL_CTX *ctx, ++ int (*callback)(SSL *ssl, void *arg)) { ++ ctx->legacy_ocsp_callback = callback; ++ return 1; ++} ++ ++int SSL_CTX_set_tlsext_status_arg(SSL_CTX *ctx, void *arg) { ++ ctx->legacy_ocsp_callback_arg = arg; ++ return 1; ++} +diff --git a/ssl/test/bssl_shim.cc b/ssl/test/bssl_shim.cc +index ae26ded..3a33d60 100644 +--- a/ssl/test/bssl_shim.cc ++++ b/ssl/test/bssl_shim.cc +@@ -495,6 +495,7 @@ static bool GetCertificate(SSL *ssl, bssl::UniquePtr *out_x509, + return false; + } + if (!config->ocsp_response.empty() && ++ !config->set_ocsp_in_callback && + !SSL_set_ocsp_response(ssl, (const uint8_t *)config->ocsp_response.data(), + config->ocsp_response.size())) { + return false; +@@ -1100,6 +1101,27 @@ static void MessageCallback(int is_write, int version, int content_type, + } + } + ++static int LegacyOCSPCallback(SSL *ssl, void *arg) { ++ const TestConfig *config = GetTestConfig(ssl); ++ if (!SSL_is_server(ssl)) { ++ return !config->fail_ocsp_callback; ++ } ++ ++ if (!config->ocsp_response.empty() && ++ config->set_ocsp_in_callback && ++ !SSL_set_ocsp_response(ssl, (const uint8_t *)config->ocsp_response.data(), ++ config->ocsp_response.size())) { ++ return SSL_TLSEXT_ERR_ALERT_FATAL; ++ } ++ if (config->fail_ocsp_callback) { ++ return SSL_TLSEXT_ERR_ALERT_FATAL; ++ } ++ if (config->decline_ocsp_callback) { ++ return SSL_TLSEXT_ERR_NOACK; ++ } ++ return SSL_TLSEXT_ERR_OK; ++} ++ + // Connect returns a new socket connected to localhost on |port| or -1 on + // error. + static int Connect(uint16_t port) { +@@ -1334,6 +1356,10 @@ static bssl::UniquePtr SetupCtx(SSL_CTX *old_ctx, + SSL_CTX_set_false_start_allowed_without_alpn(ssl_ctx.get(), 1); + } + ++ if (config->use_ocsp_callback) { ++ SSL_CTX_set_tlsext_status_cb(ssl_ctx.get(), LegacyOCSPCallback); ++ } ++ + if (old_ctx) { + uint8_t keys[48]; + if (!SSL_CTX_get_tlsext_ticket_keys(old_ctx, &keys, sizeof(keys)) || +diff --git a/ssl/test/runner/alert.go b/ssl/test/runner/alert.go +index 652e9ee..c79725e 100644 +--- a/ssl/test/runner/alert.go ++++ b/ssl/test/runner/alert.go +@@ -15,69 +15,71 @@ const ( + ) + + const ( +- alertCloseNotify alert = 0 +- alertEndOfEarlyData alert = 1 +- alertUnexpectedMessage alert = 10 +- alertBadRecordMAC alert = 20 +- alertDecryptionFailed alert = 21 +- alertRecordOverflow alert = 22 +- alertDecompressionFailure alert = 30 +- alertHandshakeFailure alert = 40 +- alertNoCertificate alert = 41 +- alertBadCertificate alert = 42 +- alertUnsupportedCertificate alert = 43 +- alertCertificateRevoked alert = 44 +- alertCertificateExpired alert = 45 +- alertCertificateUnknown alert = 46 +- alertIllegalParameter alert = 47 +- alertUnknownCA alert = 48 +- alertAccessDenied alert = 49 +- alertDecodeError alert = 50 +- alertDecryptError alert = 51 +- alertProtocolVersion alert = 70 +- alertInsufficientSecurity alert = 71 +- alertInternalError alert = 80 +- alertInappropriateFallback alert = 86 +- alertUserCanceled alert = 90 +- alertNoRenegotiation alert = 100 +- alertMissingExtension alert = 109 +- alertUnsupportedExtension alert = 110 +- alertUnrecognizedName alert = 112 +- alertUnknownPSKIdentity alert = 115 +- alertCertificateRequired alert = 116 ++ alertCloseNotify alert = 0 ++ alertEndOfEarlyData alert = 1 ++ alertUnexpectedMessage alert = 10 ++ alertBadRecordMAC alert = 20 ++ alertDecryptionFailed alert = 21 ++ alertRecordOverflow alert = 22 ++ alertDecompressionFailure alert = 30 ++ alertHandshakeFailure alert = 40 ++ alertNoCertificate alert = 41 ++ alertBadCertificate alert = 42 ++ alertUnsupportedCertificate alert = 43 ++ alertCertificateRevoked alert = 44 ++ alertCertificateExpired alert = 45 ++ alertCertificateUnknown alert = 46 ++ alertIllegalParameter alert = 47 ++ alertUnknownCA alert = 48 ++ alertAccessDenied alert = 49 ++ alertDecodeError alert = 50 ++ alertDecryptError alert = 51 ++ alertProtocolVersion alert = 70 ++ alertInsufficientSecurity alert = 71 ++ alertInternalError alert = 80 ++ alertInappropriateFallback alert = 86 ++ alertUserCanceled alert = 90 ++ alertNoRenegotiation alert = 100 ++ alertMissingExtension alert = 109 ++ alertUnsupportedExtension alert = 110 ++ alertUnrecognizedName alert = 112 ++ alertBadCertificateStatusResponse alert = 113 ++ alertUnknownPSKIdentity alert = 115 ++ alertCertificateRequired alert = 116 + ) + + var alertText = map[alert]string{ +- alertCloseNotify: "close notify", +- alertEndOfEarlyData: "end of early data", +- alertUnexpectedMessage: "unexpected message", +- alertBadRecordMAC: "bad record MAC", +- alertDecryptionFailed: "decryption failed", +- alertRecordOverflow: "record overflow", +- alertDecompressionFailure: "decompression failure", +- alertHandshakeFailure: "handshake failure", +- alertNoCertificate: "no certificate", +- alertBadCertificate: "bad certificate", +- alertUnsupportedCertificate: "unsupported certificate", +- alertCertificateRevoked: "revoked certificate", +- alertCertificateExpired: "expired certificate", +- alertCertificateUnknown: "unknown certificate", +- alertIllegalParameter: "illegal parameter", +- alertUnknownCA: "unknown certificate authority", +- alertAccessDenied: "access denied", +- alertDecodeError: "error decoding message", +- alertDecryptError: "error decrypting message", +- alertProtocolVersion: "protocol version not supported", +- alertInsufficientSecurity: "insufficient security level", +- alertInternalError: "internal error", +- alertInappropriateFallback: "inappropriate fallback", +- alertUserCanceled: "user canceled", +- alertNoRenegotiation: "no renegotiation", +- alertMissingExtension: "missing extension", +- alertUnsupportedExtension: "unsupported extension", +- alertUnrecognizedName: "unrecognized name", +- alertUnknownPSKIdentity: "unknown PSK identity", +- alertCertificateRequired: "certificate required", ++ alertCloseNotify: "close notify", ++ alertEndOfEarlyData: "end of early data", ++ alertUnexpectedMessage: "unexpected message", ++ alertBadRecordMAC: "bad record MAC", ++ alertDecryptionFailed: "decryption failed", ++ alertRecordOverflow: "record overflow", ++ alertDecompressionFailure: "decompression failure", ++ alertHandshakeFailure: "handshake failure", ++ alertNoCertificate: "no certificate", ++ alertBadCertificate: "bad certificate", ++ alertUnsupportedCertificate: "unsupported certificate", ++ alertCertificateRevoked: "revoked certificate", ++ alertCertificateExpired: "expired certificate", ++ alertCertificateUnknown: "unknown certificate", ++ alertIllegalParameter: "illegal parameter", ++ alertUnknownCA: "unknown certificate authority", ++ alertAccessDenied: "access denied", ++ alertDecodeError: "error decoding message", ++ alertDecryptError: "error decrypting message", ++ alertProtocolVersion: "protocol version not supported", ++ alertInsufficientSecurity: "insufficient security level", ++ alertInternalError: "internal error", ++ alertInappropriateFallback: "inappropriate fallback", ++ alertUserCanceled: "user canceled", ++ alertNoRenegotiation: "no renegotiation", ++ alertMissingExtension: "missing extension", ++ alertUnsupportedExtension: "unsupported extension", ++ alertBadCertificateStatusResponse: "bad certificate status response", ++ alertUnrecognizedName: "unrecognized name", ++ alertUnknownPSKIdentity: "unknown PSK identity", ++ alertCertificateRequired: "certificate required", + } + + func (e alert) String() string { +diff --git a/ssl/test/runner/runner.go b/ssl/test/runner/runner.go +index 510a48b..1a6d0f9 100644 +--- a/ssl/test/runner/runner.go ++++ b/ssl/test/runner/runner.go +@@ -4744,60 +4744,157 @@ func addStateMachineCoverageTests(config stateMachineTestConfig) { + }) + + // OCSP stapling tests. +- tests = append(tests, testCase{ +- testType: clientTest, +- name: "OCSPStapling-Client", +- config: Config{ +- MaxVersion: VersionTLS12, +- }, +- flags: []string{ +- "-enable-ocsp-stapling", +- "-expect-ocsp-response", +- base64.StdEncoding.EncodeToString(testOCSPResponse), +- "-verify-peer", +- }, +- resumeSession: true, +- }) +- tests = append(tests, testCase{ +- testType: serverTest, +- name: "OCSPStapling-Server", +- config: Config{ +- MaxVersion: VersionTLS12, +- }, +- expectedOCSPResponse: testOCSPResponse, +- flags: []string{ +- "-ocsp-response", +- base64.StdEncoding.EncodeToString(testOCSPResponse), +- }, +- resumeSession: true, +- }) +- tests = append(tests, testCase{ +- testType: clientTest, +- name: "OCSPStapling-Client-TLS13", +- config: Config{ +- MaxVersion: VersionTLS13, +- }, +- flags: []string{ +- "-enable-ocsp-stapling", +- "-expect-ocsp-response", +- base64.StdEncoding.EncodeToString(testOCSPResponse), +- "-verify-peer", +- }, +- resumeSession: true, +- }) +- tests = append(tests, testCase{ +- testType: serverTest, +- name: "OCSPStapling-Server-TLS13", +- config: Config{ +- MaxVersion: VersionTLS13, +- }, +- expectedOCSPResponse: testOCSPResponse, +- flags: []string{ +- "-ocsp-response", +- base64.StdEncoding.EncodeToString(testOCSPResponse), +- }, +- resumeSession: true, +- }) ++ for _, vers := range tlsVersions { ++ if config.protocol == dtls && !vers.hasDTLS { ++ continue ++ } ++ if vers.version == VersionSSL30 { ++ continue ++ } ++ tests = append(tests, testCase{ ++ testType: clientTest, ++ name: "OCSPStapling-Client-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ }, ++ tls13Variant: vers.tls13Variant, ++ flags: []string{ ++ "-enable-ocsp-stapling", ++ "-expect-ocsp-response", ++ base64.StdEncoding.EncodeToString(testOCSPResponse), ++ "-verify-peer", ++ }, ++ resumeSession: true, ++ }) ++ tests = append(tests, testCase{ ++ testType: serverTest, ++ name: "OCSPStapling-Server-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ }, ++ tls13Variant: vers.tls13Variant, ++ expectedOCSPResponse: testOCSPResponse, ++ flags: []string{ ++ "-ocsp-response", ++ base64.StdEncoding.EncodeToString(testOCSPResponse), ++ }, ++ resumeSession: true, ++ }) ++ ++ // The client OCSP callback is an alternate certificate ++ // verification callback. ++ tests = append(tests, testCase{ ++ testType: clientTest, ++ name: "ClientOCSPCallback-Pass-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ Certificates: []Certificate{rsaCertificate}, ++ }, ++ tls13Variant: vers.tls13Variant, ++ flags: []string{ ++ "-enable-ocsp-stapling", ++ "-use-ocsp-callback", ++ }, ++ }) ++ var expectedLocalError string ++ if !config.async { ++ // TODO(davidben): Asynchronous fatal alerts are never ++ // sent. https://crbug.com/boringssl/130. ++ expectedLocalError = "remote error: bad certificate status response" ++ } ++ tests = append(tests, testCase{ ++ testType: clientTest, ++ name: "ClientOCSPCallback-Fail-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ Certificates: []Certificate{rsaCertificate}, ++ }, ++ tls13Variant: vers.tls13Variant, ++ flags: []string{ ++ "-enable-ocsp-stapling", ++ "-use-ocsp-callback", ++ "-fail-ocsp-callback", ++ }, ++ shouldFail: true, ++ expectedLocalError: expectedLocalError, ++ expectedError: ":OCSP_CB_ERROR:", ++ }) ++ // The callback does not run if the server does not send an ++ // OCSP response. ++ certNoStaple := rsaCertificate ++ certNoStaple.OCSPStaple = nil ++ tests = append(tests, testCase{ ++ testType: clientTest, ++ name: "ClientOCSPCallback-FailNoStaple-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ Certificates: []Certificate{certNoStaple}, ++ }, ++ tls13Variant: vers.tls13Variant, ++ flags: []string{ ++ "-enable-ocsp-stapling", ++ "-use-ocsp-callback", ++ "-fail-ocsp-callback", ++ }, ++ }) ++ ++ // The server OCSP callback is a legacy mechanism for ++ // configuring OCSP, used by unreliable server software. ++ tests = append(tests, testCase{ ++ testType: serverTest, ++ name: "ServerOCSPCallback-SetInCallback-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ }, ++ tls13Variant: vers.tls13Variant, ++ expectedOCSPResponse: testOCSPResponse, ++ flags: []string{ ++ "-use-ocsp-callback", ++ "-set-ocsp-in-callback", ++ "-ocsp-response", ++ base64.StdEncoding.EncodeToString(testOCSPResponse), ++ }, ++ resumeSession: true, ++ }) ++ ++ // The callback may decline OCSP, in which case we act as if ++ // the client did not support it, even if a response was ++ // configured. ++ tests = append(tests, testCase{ ++ testType: serverTest, ++ name: "ServerOCSPCallback-Decline-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ }, ++ tls13Variant: vers.tls13Variant, ++ expectedOCSPResponse: []byte{}, ++ flags: []string{ ++ "-use-ocsp-callback", ++ "-decline-ocsp-callback", ++ "-ocsp-response", ++ base64.StdEncoding.EncodeToString(testOCSPResponse), ++ }, ++ resumeSession: true, ++ }) ++ ++ // The callback may also signal an internal error. ++ tests = append(tests, testCase{ ++ testType: serverTest, ++ name: "ServerOCSPCallback-Fail-" + vers.name, ++ config: Config{ ++ MaxVersion: vers.version, ++ }, ++ tls13Variant: vers.tls13Variant, ++ flags: []string{ ++ "-use-ocsp-callback", ++ "-fail-ocsp-callback", ++ "-ocsp-response", ++ base64.StdEncoding.EncodeToString(testOCSPResponse), ++ }, ++ shouldFail: true, ++ expectedError: ":OCSP_CB_ERROR:", ++ }) ++ } + + // Certificate verification tests. + for _, vers := range tlsVersions { +diff --git a/ssl/test/test_config.cc b/ssl/test/test_config.cc +index f50251d..3afb01b 100644 +--- a/ssl/test/test_config.cc ++++ b/ssl/test/test_config.cc +@@ -133,6 +133,10 @@ const Flag kBoolFlags[] = { + { "-expect-draft-downgrade", &TestConfig::expect_draft_downgrade }, + { "-handoff", &TestConfig::handoff }, + { "-expect-dummy-pq-padding", &TestConfig::expect_dummy_pq_padding }, ++ { "-use-ocsp-callback", &TestConfig::use_ocsp_callback }, ++ { "-set-ocsp-in-callback", &TestConfig::set_ocsp_in_callback }, ++ { "-decline-ocsp-callback", &TestConfig::decline_ocsp_callback }, ++ { "-fail-ocsp-callback", &TestConfig::fail_ocsp_callback }, + }; + + const Flag kStringFlags[] = { +diff --git a/ssl/test/test_config.h b/ssl/test/test_config.h +index fb479d1..a9eec62 100644 +--- a/ssl/test/test_config.h ++++ b/ssl/test/test_config.h +@@ -154,6 +154,10 @@ struct TestConfig { + int dummy_pq_padding_len = 0; + bool handoff = false; + bool expect_dummy_pq_padding = false; ++ bool use_ocsp_callback = false; ++ bool set_ocsp_in_callback = false; ++ bool decline_ocsp_callback = false; ++ bool fail_ocsp_callback = false; + }; + + bool ParseConfig(int argc, char **argv, TestConfig *out_initial, +-- +2.7.4 + diff --git a/patches/common/boringssl/implement-SSL_get_tlsext_status_type.patch b/patches/common/boringssl/implement-SSL_get_tlsext_status_type.patch new file mode 100644 index 00000000000..15603b94640 --- /dev/null +++ b/patches/common/boringssl/implement-SSL_get_tlsext_status_type.patch @@ -0,0 +1,32 @@ +diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h +index d04390df..0b8677ce 100644 +--- a/include/openssl/ssl.h ++++ b/include/openssl/ssl.h +@@ -4120,6 +4120,8 @@ extern "C++" OPENSSL_EXPORT void SSL_CTX_sess_set_get_cb( + // Use |SSL_enable_ocsp_stapling| instead. + OPENSSL_EXPORT int SSL_set_tlsext_status_type(SSL *ssl, int type); + ++OPENSSL_EXPORT int SSL_get_tlsext_status_type(SSL *ssl); ++ + // SSL_set_tlsext_status_ocsp_resp sets the OCSP response. It returns one on + // success and zero on error. On success, |ssl| takes ownership of |resp|, which + // must have been allocated by |OPENSSL_malloc|. +diff --git a/ssl/ssl_lib.cc b/ssl/ssl_lib.cc +index 0c004fd4..6c849b5b 100644 +--- a/ssl/ssl_lib.cc ++++ b/ssl/ssl_lib.cc +@@ -2723,6 +2723,14 @@ int SSL_set_tlsext_status_type(SSL *ssl, int type) { + return 1; + } + ++int SSL_get_tlsext_status_type(SSL *ssl) { ++ if (ssl->ocsp_stapling_enabled) { ++ return TLSEXT_STATUSTYPE_ocsp; ++ } ++ ++ return TLSEXT_STATUSTYPE_nothing; ++} ++ + int SSL_set_tlsext_status_ocsp_resp(SSL *ssl, uint8_t *resp, size_t resp_len) { + if (SSL_set_ocsp_response(ssl, resp, resp_len)) { + OPENSSL_free(resp); diff --git a/patches/common/chromium/.patches.yaml b/patches/common/chromium/.patches.yaml new file mode 100644 index 00000000000..19ef8222e2d --- /dev/null +++ b/patches/common/chromium/.patches.yaml @@ -0,0 +1,468 @@ +repo: src +patches: +- + author: Shelley Vohr + file: add_realloc.patch + description: | + Blink overrides ArrayBuffer's allocator with its own one, while Node simply + uses malloc and free, so we need to use v8's allocator in Node. As part of the + 10.6.0 upgrade, we needed to make SerializerDelegate accept an allocator + argument in its constructor, and override ReallocateBufferMemory and + FreeBufferMemory to use the allocator. We cannot simply allocate and then memcpy + when we override ReallocateBufferMemory, so we therefore need to implement + Realloc on the v8 side and correspondingly in gin. +- + author: Ales Pergl + file: build_gn.patch + description: null +- + author: deepak1556 + file: dcheck.patch + description: | + This disables some debug checks which currently fail when running the Electron + test suite. In general there should be sustained effort to have all debug checks + enabled. If you want to help, choose one of the diffs below and remove it. Then + build Electron (debug configuration) and make sure all tests pass on the CI + systems. Unfortunately the tests don't always cover the check failures, so it's + good to also run some non-trivial Electron app to verify. + + Apart from getting rid of a whole diff, you may also be able to replace one diff + with another which enables at least some of the previously disabled checks. For + example, the checks might be disabled for a whole build target, but actually + only one or two specific checks fail. Then it's better to simply comment out the + failing checks and allow the rest of the target to have them enabled. + + Please keep the following lists updated. + + The ELECTRON_NO_DCHECK build flag disables debug checks universally. + This patch applies the flag to the following GN targets: + + third_party/blink/renderer/core/loader:loader + url:url + + These files have debug checks explicitly commented out: + + base/memory/weak_ptr.cc + base/process/kill_win.cc + components/viz/service/display/program_binding.h + components/viz/service/display_embedder/server_shared_bitmap_manager.cc + content/browser/frame_host/navigation_controller_impl.cc + content/browser/frame_host/render_frame_host_impl.cc + content/browser/renderer_host/render_widget_host_view_mac.mm + ppapi/host/ppapi_host.cc + third_party/blink/renderer/core/dom/node.cc + third_party/blink/renderer/platform/wtf/text/string_impl.cc + ui/base/clipboard/clipboard_win.cc +- + author: Cheng Zhao + file: accelerator.patch + description: null +- + author: Ales Pergl + file: allow_new_privs.patch + description: null +- + author: null + file: app_indicator_icon_menu.patch + description: null +- + author: Cheng Zhao + file: blink_file_path.patch + description: null +- + author: Cheng Zhao + file: blink_local_frame.patch + description: | + According to electron/electron#3699, it is unreliable to use |unload| + event for process.exit('exit'), so we have to do that in + willReleaseScriptContext. + + However Chromium then disallowed scripting in willReleaseScriptContext + in https://codereview.chromium.org/1657583002, and crash will happen + when there is code doing that. + + This patch reverts the change to fix the crash in Electron. +- + author: null + file: blink_world_context.patch + description: null +- + author: Cheng Zhao + file: browser_compositor_mac.patch + description: null +- + author: null + file: browser_plugin_wheel.patch + description: null +- + author: null + file: build_toolchain_win_patch.patch + description: | + Patch the Windows build toolchain to generate unique PDB names + + When the PDB files generated by the `static_library` build are + packaged for distribution they are all copied to a single folder, + some of the PDB files have identical names so they end up + overwriting each other. The missing PDB files cause linker warnings + when building Electron in Release mode, and make it more difficult + to debug release builds. + + This patch modifies the PDB naming convention for the + `static_library` build configuration to ensure PDB names are unique. + For example, instead of generating `obj/ui/base/base_cc.pdb` the + build will now generate `obj/ui/base/obj_ui_base_base_cc.pdb`. +- + author: Cheng Zhao + file: can_create_window.patch + description: null +- + author: null + file: compositor_delegate.patch + description: null +- + author: null + file: desktop_screen_win.patch + description: null +- + author: Cheng Zhao + file: disable_hidden.patch + description: null +- + author: Cheng Zhao + file: dom_storage_map.patch + description: null +- + author: deepak1556 + file: frame_host_manager.patch + description: null +- + author: Tony Ganch + file: latency_info.patch + description: null +- + author: Cheng Zhao + file: net_url_request_job.patch + description: null +- + author: Aleksei Kuzmin + file: no_stack_dumping.patch + description: null +- + author: deepak1556 + file: out_of_process_instance.patch + description: null +- + author: Aleksei Kuzmin + file: protobuf_build_gn.patch + description: null +- + author: null + file: render_widget_host_view_base.patch + description: null +- + author: Cheng Zhao + file: render_widget_host_view_mac.patch + description: null +- + author: null + file: scoped_clipboard_writer.patch + description: null +- + author: deepak1556 + file: stream_resource_handler.patch + description: null +- + author: null + file: thread_capabilities.patch + description: | + Chromium automatically drops all capabilities of renderer threads in + Linux, which may cause issues in a context like Electron, where the main + and renderer threads are supposed to keep inherited permissions over the + system. + + See https://github.com/atom/electron/issues/3666 +- + author: Cheng Zhao + file: use_transparent_window.patch + description: null +- + author: null + file: web_contents.patch + description: null +- + author: Milan Burda + file: webgl_context_attributes.patch + description: null +- + author: null + file: webview_cross_drag.patch + description: null +- + author: Cheng Zhao + file: worker_context_will_destroy.patch + description: null +- + author: null + file: webui_in_subframes.patch + description: null +- + author: Aleksei Kuzmin + file: export_blink_webdisplayitemlist.patch + description: null +- + author: Aleksei Kuzmin + file: statically_build_power_save_blocker.patch + description: null +- + author: Tomas Rycl + file: browser_plugin_guest.patch + description: null +- + author: Aleksei Kuzmin + file: disable_user_gesture_requirement_for_beforeunload_dialogs.patch + description: See https://github.com/electron/electron/issues/10754 +- + author: Aleksei Kuzmin + file: add_atomic_lib_to_dependencies_even_for_sysroot_builds.patch + description: null +- + author: Cheng Zhao + file: gin_enable_disable_v8_platform.patch + description: null +- + author: deepak1556 + file: disable-recursive-surface-sync.patch + description: null +- + author: deepak1556 + file: blink-worker-enable-csp-in-file-scheme.patch + description: null +- + author: Cheng Zhao + file: fix-arm64-linking-error.patch + description: Do not use system freetype for arm64 +- + author: Heilig Benedek + file: disable-redraw-lock.patch + description: | + Chromium uses a custom window titlebar implementation on Windows when DWM + is disabled (Windows 7 and earlier, non Aero theme). The native titlebar + sometimes painted over this custom titlebar, so a workaround was put in + place to lock redraws in reaction to certain events if DWM is disabled, + since the code assumes that in that case, the custom titlebar is painted. + Electron forces the use of the native titlebar, which the workaround doesn't + take into account, and still locks redraws, causing weird repainting issues + in electron (and other applications). This patch provides a way to disable + the redraw locking mechanism, which fixes these issues. The electron issue + can be found at https://github.com/electron/electron/issues/1821 +- + author: Nitish Sakhawalkar + file: v8_context_snapshot_generator.patch + description: | + v8_context_snapshot_generator is a build time executable. + The patch adds the config. +# - + # author: Tomas Rycl + # file: crashpad-disabled-windows.patch + # description: | + # On Windows Electron does not link Crashpad. This causes linking + # errors with Chromium where it is enabled by default. + # This patch will disable Crashpad in Chromium using fallback + # mechanism which uses Breakpad. +- + author: Jeremy Apthorp + file: boringssl_build_gn.patch + description: | + Build BoringSSL with some extra functions that nodejs needs. Only affects + the GN build; with the GYP build, nodejs is still built with OpenSSL. +- + author: deepak1556 + file: pepper_flash.patch + description: | + Allows building chrome pepper flash integration for Electron. +- + author: Cheng Zhao + file: no_cache_storage_check.patch + description: | + Do not check for unique origin in CacheStorage, in Electron we may have + scripts running without an origin. +- + author: Cheng Zhao + file: blink_fix_prototype_assert.patch + description: | + A recent Chromium change has accidentally added assertion for the case when + a new window object may not have a prototype attached. In Electron it may + happen when preventDefault for a native new-window event. + https://chromium.googlesource.com/chromium/src/+/f47b361887a31cccf42a6e21a82bccf28372bdaa%5E%21 + In the long term we should investigate why it happened, and take a more + formal fix. But for now I'm just make this assertion silently pass away. +- + author: Cheng Zhao + file: disable_scroll_begin_dcheck.patch + description: | + When testing https://github.com/electron/electron/issues/13137 I have met + these assertions. I grouped them together since they are all related to the + ScrollBegin event. +- + author: Jeremy Apthorp + file: libgtkui_export.patch + description: | + Export libgtkui symbols for the GN component build. +- + author: Jeremy Apthorp + file: gtk_visibility.patch + description: | + Allow electron and brightray to depend on GTK in the GN build. +- + author: Jeremy Apthorp + file: sysroot.patch + description: | + Make chrome's install-sysroot scripts point to our custom sysroot builds, + which include extra deps that Electron needs (e.g. libnotify) +- + author: Cheng Zhao + file: mas_blink_no_private_api.patch + description: | + Guard usages in chromium code of private Mac APIs by MAS_BUILD, so they can + be excluded for people who want to submit their apps to the Mac App store. +- + author: Cheng Zhao + file: mas_no_private_api.patch + description: | + Guard usages in blink of private Mac APIs by MAS_BUILD, so they can be + excluded for people who want to submit their apps to the Mac App store. +- + author: Jeremy Apthorp + file: resource_file_conflict.patch + description: | + Resolve conflict between //chrome's .pak files and //electron's. The paths + that chrome code hardcodes require that we generate resources at these + paths, but GN throws errors if there are multiple targets that generate the + same files. +- + author: Cheng Zhao + file: scroll_bounce_flag.patch + description: | + Patch to make scrollBounce option work. +- + author: Birunthan Mohanathas + file: backport_d65792a.patch + description: | + https://chromium-review.googlesource.com/c/chromium/src/+/1105698 + Fixes https://github.com/electron/electron/issues/13256 +- + author: Cheng Zhao + file: webview_reattach.patch + description: | + Backports https://chromium-review.googlesource.com/c/chromium/src/+/1161391 + Fixes webview not working after renderer process restarted. +- + author: Jeremy Apthorp + file: mas-cfisobjc.patch + description: | + Removes usage of the _CFIsObjC private API. +- + author: Jeremy Apthorp + file: mas-cgdisplayusesforcetogray.patch + description: | + Removes usage of the CGDisplayUsesForceToGray private API. +- + author: Jeremy Apthorp + file: mas-audiodeviceduck.patch + description: | + Removes usage of the AudioDeviceDuck private API. +- + author: Jeremy Apthorp + file: mas-lssetapplicationlaunchservicesserverconnectionstatus.patch + description: | + Removes usage of the _LSSetApplicationLaunchServicesServerConnectionStatus + private API. +- + author: Cheng Zhao + file: allow_webview_file_url.patch + description: | + Allow webview to load non-web URLs. +- + author: John Kleinschmidt + file: windows_cc_wrapper.patch + description: | + Allow use of cc_wrapper (eg sccache). +- + author: Shelley Vohr + file: enable_osr_components.patch + description: | + Add MouseWheelPhaseHandler for OSR. +- + author: Zac Walker + file: ignore_rc_check.patch + description: | + Dont compare RC.exe and RC.py output. + FIXME: It has to be reverted once the script is fixed. +- + author: Aleksei Kuzmin + file: enable_widevine.patch + description: | + Turns `enable_widevine` flag on by default on Mac and Windows. + Electron needs that flag to be enabled on those paltforms, + but there's no way to conditionally set it during a `gn gen` call. +- + author: deepak1556 + file: content_browser_manifest.patch + description: | + Allow content_browser service to access GeolocationControl + interface from device service. +- + author: deepak1556 + file: chrome_key_systems.patch + description: | + Disable persiste licence support check for widevine cdm, + as its not supported in the current version of chrome. +- + author: Charles Kerr + file: allow_nested_error_trackers.patch + description: | + Only one X11ErrorTracker should exist at a time, but upstream has a bug + where two can exist if running in headless mode -- + ui::(anonymous namespace)::SupportsEWMH() [inner tracker is created] + ui::WmSupportsHint() + ui::IsX11WindowFullScreen() + ui::ScreensaverWindowFinder::IsScreensaverWindow() + ui::ScreensaverWindowFinder::ShouldStopIterating() + ui::EnumerateTopLevelWindows() + ui::ScreensaverWindowFinder::ScreensaverWindowExists() [outer tracker created] + ui::CheckIdleStateIsLocked() + ui::CalculateIdleState() + Removal of either tracker could have side-effects in some code paths, + so this is probably better handled upstream. This patch tries to do the + least harm in the interim by removing the check that prevents more than + one tracker from existing at a time. +- + author: Samuel Attard + file: blink_initialization_order.patch + description: | + Backport of https://chromium-review.googlesource.com/c/chromium/src/+/1030530 + to fix the order of V8 and Blink initialization. Also fixes order + of DidCreateScriptContext notification with initialization of window globals + to fix electron/electron#13787. The backport landed in Chromium 67 but the + DidCreateScriptContext re-ordering needs to be upstreamed or kept indefinitely +- + author: zcbenz + file: disable_detach_webview_frame.patch + description: | + Don't detach the frame for webview, we will manage the WebContents + manually. + This is part of the fixes for https://github.com/electron/electron/issues/14211. + We should revisit this bug after upgrading to newer versions of Chrome, + this patch was introduced in Chrome 66. +- + author: deepak1556 + file: ssl_security_state_tab_helper.patch + description: | + Allows populating security tab info for devtools in Electron. +- + author: Jeremy Apthorp + file: leveldb_ssize_t.patch + description: | + Fix conflict between leveldb & node's definition of ssize_t on + Windows by preventing leveldb from re-defining the type if it's + already defined. diff --git a/patches/common/chromium/accelerator.patch b/patches/common/chromium/accelerator.patch new file mode 100644 index 00000000000..539ba9dee42 --- /dev/null +++ b/patches/common/chromium/accelerator.patch @@ -0,0 +1,103 @@ +diff --git a/ui/base/accelerators/accelerator.cc b/ui/base/accelerators/accelerator.cc +index a6756c2..5352958 100644 +--- a/ui/base/accelerators/accelerator.cc ++++ b/ui/base/accelerators/accelerator.cc +@@ -11,6 +11,7 @@ + #include "base/logging.h" + #include "base/strings/strcat.h" + #include "base/strings/string_util.h" ++#include "base/strings/stringprintf.h" + #include "base/strings/utf_string_conversions.h" + #include "build/build_config.h" + #include "ui/base/l10n/l10n_util.h" +@@ -21,9 +22,7 @@ + #include + #endif + +-#if !defined(OS_WIN) && (defined(USE_AURA) || defined(OS_MACOSX)) + #include "ui/events/keycodes/keyboard_code_conversion.h" +-#endif + + namespace ui { + +@@ -145,7 +144,17 @@ base::string16 Accelerator::GetShortcutText() const { + shortcut = KeyCodeToName(key_code_); + #endif + ++ unsigned int flags = 0; + if (shortcut.empty()) { ++ if (IsShiftDown()) ++ flags = ui::EF_SHIFT_DOWN; ++ const uint16_t c = DomCodeToUsLayoutCharacter( ++ UsLayoutKeyboardCodeToDomCode(key_code_), flags); ++ if (c != 0) { ++ shortcut = ++ static_cast( ++ base::ToUpperASCII(static_cast(c))); ++ } + #if defined(OS_WIN) + // Our fallback is to try translate the key code to a regular character + // unless it is one of digits (VK_0 to VK_9). Some keyboard +@@ -154,17 +163,20 @@ base::string16 Accelerator::GetShortcutText() const { + // accent' for '0'). For display in the menu (e.g. Ctrl-0 for the + // default zoom level), we leave VK_[0-9] alone without translation. + wchar_t key; +- if (base::IsAsciiDigit(key_code_)) ++ if (base::IsAsciiDigit(key_code_)) { + key = static_cast(key_code_); +- else +- key = LOWORD(::MapVirtualKeyW(key_code_, MAPVK_VK_TO_CHAR)); +- shortcut += key; +-#elif defined(USE_AURA) || defined(OS_MACOSX) +- const uint16_t c = DomCodeToUsLayoutCharacter( +- UsLayoutKeyboardCodeToDomCode(key_code_), false); +- if (c != 0) +- shortcut += +- static_cast(base::ToUpperASCII(c)); ++ shortcut = key; ++ } ++#endif ++ if (key_code_ > VKEY_F1 && key_code_ <= VKEY_F24) ++ shortcut = base::UTF8ToUTF16( ++ base::StringPrintf("F%d", key_code_ - VKEY_F1 + 1)); ++ } else if (IsShiftDown()) { ++#if defined(OS_MACOSX) ++ const base::char16 kShiftSymbol[] = {0x21e7, 0}; ++ shortcut = kShiftSymbol; ++#else ++ shortcut = l10n_util::GetStringFUTF16(IDS_APP_SHIFT_MODIFIER, shortcut); + #endif + } + +@@ -221,15 +233,12 @@ base::string16 Accelerator::GetShortcutText() const { + + base::string16 Accelerator::ApplyLongFormModifiers( + base::string16 shortcut) const { +- if (IsShiftDown()) +- shortcut = l10n_util::GetStringFUTF16(IDS_APP_SHIFT_MODIFIER, shortcut); +- + // Note that we use 'else-if' in order to avoid using Ctrl+Alt as a shortcut. + // See http://blogs.msdn.com/oldnewthing/archive/2004/03/29/101121.aspx for + // more information. + if (IsCtrlDown()) + shortcut = l10n_util::GetStringFUTF16(IDS_APP_CONTROL_MODIFIER, shortcut); +- else if (IsAltDown()) ++ if (IsAltDown()) + shortcut = l10n_util::GetStringFUTF16(IDS_APP_ALT_MODIFIER, shortcut); + + if (IsCmdDown()) { +@@ -249,14 +258,12 @@ base::string16 Accelerator::ApplyShortFormModifiers( + base::string16 shortcut) const { + const base::char16 kCommandSymbol[] = {0x2318, 0}; + const base::char16 kCtrlSymbol[] = {0x2303, 0}; +- const base::char16 kShiftSymbol[] = {0x21e7, 0}; + const base::char16 kOptionSymbol[] = {0x2325, 0}; + const base::char16 kNoSymbol[] = {0}; + + std::vector parts; + parts.push_back(base::string16(IsCtrlDown() ? kCtrlSymbol : kNoSymbol)); + parts.push_back(base::string16(IsAltDown() ? kOptionSymbol : kNoSymbol)); +- parts.push_back(base::string16(IsShiftDown() ? kShiftSymbol : kNoSymbol)); + parts.push_back(base::string16(IsCmdDown() ? kCommandSymbol : kNoSymbol)); + parts.push_back(shortcut); + return base::StrCat(parts); diff --git a/patches/common/chromium/add_atomic_lib_to_dependencies_even_for_sysroot_builds.patch b/patches/common/chromium/add_atomic_lib_to_dependencies_even_for_sysroot_builds.patch new file mode 100644 index 00000000000..3b55672a31b --- /dev/null +++ b/patches/common/chromium/add_atomic_lib_to_dependencies_even_for_sysroot_builds.patch @@ -0,0 +1,13 @@ +diff --git a/base/BUILD.gn b/base/BUILD.gn +index b674e703617d..5a7a11d816cf 100644 +--- a/base/BUILD.gn ++++ b/base/BUILD.gn +@@ -1131,7 +1131,7 @@ component("base") { + # Needed for if using newer C++ library than sysroot, except if + # building inside the cros_sdk environment - use host_toolchain as a + # more robust check for this. +- if (!use_sysroot && (is_android || (is_linux && !is_chromecast)) && ++ if ((is_android || (is_linux && !is_chromecast)) && + host_toolchain != "//build/toolchain/cros:host") { + libs = [ "atomic" ] + } diff --git a/patches/common/chromium/add_realloc.patch b/patches/common/chromium/add_realloc.patch new file mode 100644 index 00000000000..2a6b67737be --- /dev/null +++ b/patches/common/chromium/add_realloc.patch @@ -0,0 +1,70 @@ +diff --git a/gin/array_buffer.cc b/gin/array_buffer.cc +index f84934bfd712..63bce16a9d06 100644 +--- a/gin/array_buffer.cc ++++ b/gin/array_buffer.cc +@@ -43,6 +43,10 @@ void* ArrayBufferAllocator::AllocateUninitialized(size_t length) { + return malloc(length); + } + ++void* ArrayBufferAllocator::Realloc(void* data, size_t length) { ++ return realloc(data, length); ++} ++ + void ArrayBufferAllocator::Free(void* data, size_t length) { + free(data); + } +diff --git a/gin/array_buffer.h b/gin/array_buffer.h +index 2aef366ac819..c037808a9bb3 100644 +--- a/gin/array_buffer.h ++++ b/gin/array_buffer.h +@@ -21,6 +21,7 @@ class ArrayBufferAllocator : public v8::ArrayBuffer::Allocator { + public: + void* Allocate(size_t length) override; + void* AllocateUninitialized(size_t length) override; ++ void* Realloc(void* data, size_t length) override; + void Free(void* data, size_t length) override; + + GIN_EXPORT static ArrayBufferAllocator* SharedInstance(); +diff --git a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc +index 053babce1051..e33d6d4ceb5a 100644 +--- a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc ++++ b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc +@@ -121,6 +121,11 @@ void* ArrayBufferContents::AllocateMemoryOrNull(size_t size, + return AllocateMemoryWithFlags(size, policy, base::PartitionAllocReturnNull); + } + ++void* ArrayBufferContents::Realloc(void* data, size_t size) { ++ return Partitions::ArrayBufferPartition()->Realloc(data, size, ++ WTF_HEAP_PROFILER_TYPE_NAME(ArrayBufferContents)); ++} ++ + void ArrayBufferContents::FreeMemory(void* data) { + Partitions::ArrayBufferPartition()->Free(data); + } +diff --git a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h +index 809229caa872..6248ad32d6b0 100644 +--- a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h ++++ b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h +@@ -178,6 +178,7 @@ class WTF_EXPORT ArrayBufferContents { + void CopyTo(ArrayBufferContents& other); + + static void* AllocateMemoryOrNull(size_t, InitializationPolicy); ++ static void* Realloc(void* data, size_t); + static void FreeMemory(void*); + static DataHandle CreateDataHandle(size_t, InitializationPolicy); + static void Initialize( +diff --git a/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc b/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc +index cf2762ede559..f065b5ebafb8 100644 +--- a/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc ++++ b/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc +@@ -555,6 +555,10 @@ class ArrayBufferAllocator : public v8::ArrayBuffer::Allocator { + size, WTF::ArrayBufferContents::kDontInitialize); + } + ++ void* Realloc(void* data, size_t size) override { ++ return WTF::ArrayBufferContents::Realloc(data, size); ++ } ++ + void Free(void* data, size_t size) override { + WTF::ArrayBufferContents::FreeMemory(data); + } diff --git a/patches/common/chromium/allow_nested_error_trackers.patch b/patches/common/chromium/allow_nested_error_trackers.patch new file mode 100644 index 00000000000..17bae92aa8a --- /dev/null +++ b/patches/common/chromium/allow_nested_error_trackers.patch @@ -0,0 +1,13 @@ +diff --git a/ui/gfx/x/x11_error_tracker.cc b/ui/gfx/x/x11_error_tracker.cc +index af031de356c5..2a5c18dc473a 100644 +--- a/ui/gfx/x/x11_error_tracker.cc ++++ b/ui/gfx/x/x11_error_tracker.cc +@@ -24,7 +24,7 @@ namespace gfx { + X11ErrorTracker::X11ErrorTracker() { + // This is a non-exhaustive check for incorrect usage. It disallows nested + // X11ErrorTracker instances on the same thread. +- DCHECK(g_handler == NULL); ++ // DCHECK(g_handler == NULL); + g_handler = this; + XSync(GetXDisplay(), False); + old_handler_ = XSetErrorHandler(X11ErrorHandler); diff --git a/patches/common/chromium/allow_new_privs.patch b/patches/common/chromium/allow_new_privs.patch new file mode 100644 index 00000000000..ea19187fd29 --- /dev/null +++ b/patches/common/chromium/allow_new_privs.patch @@ -0,0 +1,13 @@ +diff --git a/base/process/launch.h b/base/process/launch.h +index 20b76fc..9db73bf 100644 +--- a/base/process/launch.h ++++ b/base/process/launch.h +@@ -147,7 +147,7 @@ struct BASE_EXPORT LaunchOptions { + + // By default, child processes will have the PR_SET_NO_NEW_PRIVS bit set. If + // true, then this bit will not be set in the new child process. +- bool allow_new_privs = false; ++ bool allow_new_privs = true; + + // Sets parent process death signal to SIGKILL. + bool kill_on_parent_death = false; diff --git a/patches/common/chromium/allow_webview_file_url.patch b/patches/common/chromium/allow_webview_file_url.patch new file mode 100644 index 00000000000..af180d1902e --- /dev/null +++ b/patches/common/chromium/allow_webview_file_url.patch @@ -0,0 +1,13 @@ +diff --git a/content/browser/loader/resource_dispatcher_host_impl.cc b/content/browser/loader/resource_dispatcher_host_impl.cc +index 0c57d20..0916ed0 100644 +--- a/content/browser/loader/resource_dispatcher_host_impl.cc ++++ b/content/browser/loader/resource_dispatcher_host_impl.cc +@@ -1870,6 +1870,8 @@ void ResourceDispatcherHostImpl::BeginNavigationRequest( + !policy->IsWebSafeScheme(info.common_params.url.scheme()) && + !is_external_protocol; + ++ non_web_url_in_guest = false; ++ + if (is_shutdown_ || non_web_url_in_guest || + (delegate_ && !delegate_->ShouldBeginRequest( + info.common_params.method, diff --git a/patches/common/chromium/app_indicator_icon_menu.patch b/patches/common/chromium/app_indicator_icon_menu.patch new file mode 100644 index 00000000000..baa32495cd7 --- /dev/null +++ b/patches/common/chromium/app_indicator_icon_menu.patch @@ -0,0 +1,13 @@ +diff --git a/chrome/browser/ui/libgtkui/app_indicator_icon_menu.cc b/chrome/browser/ui/libgtkui/app_indicator_icon_menu.cc +index 91674b9..8a4c391 100644 +--- a/chrome/browser/ui/libgtkui/app_indicator_icon_menu.cc ++++ b/chrome/browser/ui/libgtkui/app_indicator_icon_menu.cc +@@ -116,7 +116,7 @@ void AppIndicatorIconMenu::OnMenuItemActivated(GtkWidget* menu_item) { + return; + + // The menu item can still be activated by hotkeys even if it is disabled. +- if (menu_model_->IsEnabledAt(id)) ++ if (model->IsEnabledAt(id)) + ExecuteCommand(model, id); + } + diff --git a/patches/common/chromium/backport_35dabc0.patch b/patches/common/chromium/backport_35dabc0.patch new file mode 100644 index 00000000000..9a87158dfb0 --- /dev/null +++ b/patches/common/chromium/backport_35dabc0.patch @@ -0,0 +1,23 @@ +diff --git a/content/browser/service_worker/service_worker_version.cc b/content/browser/service_worker/service_worker_version.cc +index 2417abcfdae2..13a06d02e012 100644 +--- a/content/browser/service_worker/service_worker_version.cc ++++ b/content/browser/service_worker/service_worker_version.cc +@@ -53,9 +53,6 @@ + #include "third_party/WebKit/public/web/WebConsoleMessage.h" + + namespace content { +- +-using StatusCallback = ServiceWorkerVersion::StatusCallback; +- + namespace { + + // Timeout for an installed worker to start. +@@ -103,7 +100,7 @@ void RunCallbacks(ServiceWorkerVersion* version, + + // An adapter to run a |callback| after StartWorker. + void RunCallbackAfterStartWorker(base::WeakPtr version, +- StatusCallback callback, ++ ServiceWorkerVersion::StatusCallback callback, + ServiceWorkerStatusCode status) { + if (status == SERVICE_WORKER_OK && + version->running_status() != EmbeddedWorkerStatus::RUNNING) { diff --git a/patches/common/chromium/backport_953144.patch b/patches/common/chromium/backport_953144.patch new file mode 100644 index 00000000000..f49d774ff40 --- /dev/null +++ b/patches/common/chromium/backport_953144.patch @@ -0,0 +1,64 @@ +diff --git a/content/shell/browser/shell_devtools_frontend.cc b/content/shell/browser/shell_devtools_frontend.cc +index 3b3221a..6447347 100644 +--- a/content/shell/browser/shell_devtools_frontend.cc ++++ b/content/shell/browser/shell_devtools_frontend.cc +@@ -19,8 +19,8 @@ + namespace { + static GURL GetFrontendURL() { + int port = ShellDevToolsManagerDelegate::GetHttpHandlerPort(); +- return GURL( +- base::StringPrintf("http://127.0.0.1:%d/devtools/inspector.html", port)); ++ return GURL(base::StringPrintf( ++ "http://127.0.0.1:%d/devtools/devtools_app.html", port)); + } + } // namespace + +diff --git a/third_party/WebKit/Source/devtools/BUILD.gn b/third_party/WebKit/Source/devtools/BUILD.gn +index 952b922..9e7b4bf 100644 +--- a/third_party/WebKit/Source/devtools/BUILD.gn ++++ b/third_party/WebKit/Source/devtools/BUILD.gn +@@ -1048,7 +1048,6 @@ + "$resources_out_dir/cm_modes/cm_modes_module.js", + "$resources_out_dir/emulated_devices/emulated_devices_module.js", + "$resources_out_dir/product_registry_impl/product_registry_impl_module.js", +- "$resources_out_dir/screencast/screencast_module.js", + ] + + devtools_applications = [ +diff --git a/third_party/WebKit/Source/devtools/front_end/inspector.json b/third_party/WebKit/Source/devtools/front_end/inspector.json +index 36c222f..dc2149a 100644 +--- a/third_party/WebKit/Source/devtools/front_end/inspector.json ++++ b/third_party/WebKit/Source/devtools/front_end/inspector.json +@@ -1,6 +1,6 @@ + { + "modules" : [ +- { "name": "screencast", "type": "remote" } ++ { "name": "screencast", "type": "autostart" } + ], + "extends": "devtools_app", + "has_html": true +diff --git a/third_party/WebKit/Source/devtools/front_end/main/Main.js b/third_party/WebKit/Source/devtools/front_end/main/Main.js +index 4c9d9aa..e6d73b1 100644 +--- a/third_party/WebKit/Source/devtools/front_end/main/Main.js ++++ b/third_party/WebKit/Source/devtools/front_end/main/Main.js +@@ -212,19 +212,8 @@ + this._registerForwardedShortcuts(); + this._registerMessageSinkListener(); + +- // Pick first app we could instantiate (for test harness). +- for (const extension of self.runtime.extensions(Common.AppProvider)) { +- try { +- const instance = await extension.instance(); +- if (instance) { +- this._showAppUI(instance); +- break; +- } +- } catch (e) { +- console.error(e); +- } +- } + Main.Main.timeEnd('Main._createAppUI'); ++ this._showAppUI(await self.runtime.extension(Common.AppProvider).instance()); + } + + /** diff --git a/patches/common/chromium/backport_d65792a.patch b/patches/common/chromium/backport_d65792a.patch new file mode 100644 index 00000000000..3d3973cb465 --- /dev/null +++ b/patches/common/chromium/backport_d65792a.patch @@ -0,0 +1,12 @@ +diff --git a/ui/views/widget/widget.cc b/ui/views/widget/widget.cc +index bf4b1d0..a3b72c4 100644 +@@ -995,7 +996,8 @@ + + void Widget::OnSizeConstraintsChanged() { + native_widget_->OnSizeConstraintsChanged(); +- non_client_view_->SizeConstraintsChanged(); ++ if (non_client_view_) ++ non_client_view_->SizeConstraintsChanged(); + } + + void Widget::OnOwnerClosing() {} diff --git a/patches/common/chromium/backport_ef091c206.patch b/patches/common/chromium/backport_ef091c206.patch new file mode 100644 index 00000000000..1aeb6049355 --- /dev/null +++ b/patches/common/chromium/backport_ef091c206.patch @@ -0,0 +1,29 @@ +ef091c206803ebe507755cb65a1942b097fbeb32 +diff --git a/gpu/command_buffer/service/sync_point_manager.cc b/gpu/command_buffer/service/sync_point_manager.cc +index 7fdf99e7e134..ac0811194c24 100644 +--- a/gpu/command_buffer/service/sync_point_manager.cc ++++ b/gpu/command_buffer/service/sync_point_manager.cc +@@ -133,7 +133,6 @@ void SyncPointOrderData::FinishProcessingOrderNumber(uint32_t order_num) { + } + + for (OrderFence& order_fence : ensure_releases) { +- DLOG(ERROR) << "Client did not release sync token as expected"; + order_fence.client_state->EnsureWaitReleased(order_fence.fence_release, + order_fence.release_callback); + } +@@ -156,7 +155,6 @@ bool SyncPointOrderData::ValidateReleaseOrderNumber( + // We should have an unprocessed order number lower than the wait order + // number for the wait to be valid. It's not possible for wait order number to + // equal next unprocessed order number, but we handle that defensively. +- DCHECK_NE(wait_order_num, unprocessed_order_nums_.front()); + if (wait_order_num <= unprocessed_order_nums_.front()) + return false; + +@@ -309,6 +307,7 @@ void SyncPointClientState::EnsureWaitReleased(uint64_t release, + + if (call_callback) { + // This effectively releases the wait without releasing the fence. ++ DLOG(ERROR) << "Client did not release sync token as expected"; + callback.Run(); + } + } diff --git a/patches/common/chromium/blink-worker-enable-csp-in-file-scheme.patch b/patches/common/chromium/blink-worker-enable-csp-in-file-scheme.patch new file mode 100644 index 00000000000..2d310e81610 --- /dev/null +++ b/patches/common/chromium/blink-worker-enable-csp-in-file-scheme.patch @@ -0,0 +1,12 @@ +diff --git a/third_party/blink/renderer/core/workers/worker_classic_script_loader.cc b/third_party/blink/renderer/core/workers/worker_classic_script_loader.cc +index bdd886eff5e3..42a3f0ef6e55 100644 +--- a/third_party/blink/renderer/core/workers/worker_classic_script_loader.cc ++++ b/third_party/blink/renderer/core/workers/worker_classic_script_loader.cc +@@ -255,7 +255,6 @@ void WorkerScriptLoader::ProcessContentSecurityPolicy( + // document (which is implemented in WorkerMessagingProxy, and + // m_contentSecurityPolicy should be left as nullptr to inherit the policy). + if (!response.Url().ProtocolIs("blob") && +- !response.Url().ProtocolIs("file") && + !response.Url().ProtocolIs("filesystem")) { + content_security_policy_ = ContentSecurityPolicy::Create(); + content_security_policy_->SetOverrideURLForSelf(response.Url()); diff --git a/patches/common/chromium/blink_file_path.patch b/patches/common/chromium/blink_file_path.patch new file mode 100644 index 00000000000..73528c3e57e --- /dev/null +++ b/patches/common/chromium/blink_file_path.patch @@ -0,0 +1,26 @@ +diff --git a/third_party/blink/renderer/core/fileapi/file.h b/third_party/blink/renderer/core/fileapi/file.h +index 0bfe29512050..81439f7ab8f7 100644 +--- a/third_party/blink/renderer/core/fileapi/file.h ++++ b/third_party/blink/renderer/core/fileapi/file.h +@@ -170,6 +170,9 @@ class CORE_EXPORT File final : public Blob { + } + const String& name() const { return name_; } + ++ // Getter for the path IDL attribute. ++ const String& path() const { return GetPath(); } ++ + // Getter for the lastModified IDL attribute, + // http://dev.w3.org/2006/webapi/FileAPI/#file-attrs + long long lastModified() const; +diff --git a/third_party/blink/renderer/core/fileapi/file.idl b/third_party/blink/renderer/core/fileapi/file.idl +index df954bc8f818..4683b2853bb4 100644 +--- a/third_party/blink/renderer/core/fileapi/file.idl ++++ b/third_party/blink/renderer/core/fileapi/file.idl +@@ -32,6 +32,7 @@ + Exposed=(Window,Worker) + ] interface File : Blob { + readonly attribute DOMString name; ++ readonly attribute DOMString path; + readonly attribute long long lastModified; + + // Non-standard APIs diff --git a/patches/common/chromium/blink_fix_prototype_assert.patch b/patches/common/chromium/blink_fix_prototype_assert.patch new file mode 100644 index 00000000000..86edf7b5b88 --- /dev/null +++ b/patches/common/chromium/blink_fix_prototype_assert.patch @@ -0,0 +1,17 @@ +cdiff --git a/third_party/blink/renderer/platform/bindings/v8_object_constructor.cc b/third_party/blink/renderer/platform/bindings/v8_object_constructor.cc +index aedc832..8c26681 100644 +--- a/third_party/blink/renderer/platform/bindings/v8_object_constructor.cc ++++ b/third_party/blink/renderer/platform/bindings/v8_object_constructor.cc +@@ -94,8 +94,10 @@ v8::Local V8ObjectConstructor::CreateInterfaceObject( + bool get_prototype_value = + interface_object->Get(context, V8AtomicString(isolate, "prototype")) + .ToLocal(&prototype_value); +- CHECK(get_prototype_value); +- CHECK(prototype_value->IsObject()); ++ // CHECK(get_prototype_value); ++ // CHECK(prototype_value->IsObject()); ++ if (!get_prototype_value || !prototype_value->IsObject()) ++ return v8::Local(); + + prototype_object = prototype_value.As(); + if (prototype_object->InternalFieldCount() == diff --git a/patches/common/chromium/blink_initialization_order.patch b/patches/common/chromium/blink_initialization_order.patch new file mode 100644 index 00000000000..21356ad5f59 --- /dev/null +++ b/patches/common/chromium/blink_initialization_order.patch @@ -0,0 +1,18 @@ +diff --git a/third_party/blink/renderer/bindings/core/v8/local_window_proxy.cc b/third_party/blink/renderer/bindings/core/v8/local_window_proxy.cc +index 33d958fb31ae..47efe62650aa 100644 +--- a/third_party/blink/renderer/bindings/core/v8/local_window_proxy.cc ++++ b/third_party/blink/renderer/bindings/core/v8/local_window_proxy.cc +@@ -170,11 +170,11 @@ void LocalWindowProxy::Initialize() { + GetFrame()->IsMainFrame()); + MainThreadDebugger::Instance()->ContextCreated(script_state_.get(), + GetFrame(), origin); ++ ++ InstallConditionalFeatures(); + GetFrame()->Client()->DidCreateScriptContext(context, world_->GetWorldId()); + } + +- InstallConditionalFeatures(); +- + if (World().IsMainWorld()) { + GetFrame()->Loader().DispatchDidClearWindowObjectInMainWorld(); + } diff --git a/patches/common/chromium/blink_local_frame.patch b/patches/common/chromium/blink_local_frame.patch new file mode 100644 index 00000000000..c3a6b1aedb9 --- /dev/null +++ b/patches/common/chromium/blink_local_frame.patch @@ -0,0 +1,26 @@ +diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc +index 97a5393d40b4..04f88dd2ea15 100644 +--- a/third_party/blink/renderer/core/frame/local_frame.cc ++++ b/third_party/blink/renderer/core/frame/local_frame.cc +@@ -303,10 +303,6 @@ void LocalFrame::Detach(FrameDetachType type) { + } + CHECK(!view_ || !view_->IsAttached()); + +- // This is the earliest that scripting can be disabled: +- // - FrameLoader::Detach() can fire XHR abort events +- // - Document::Shutdown() can dispose plugins which can run script. +- ScriptForbiddenScope forbid_script; + if (!Client()) + return; + +@@ -316,6 +312,10 @@ void LocalFrame::Detach(FrameDetachType type) { + // Notify ScriptController that the frame is closing, since its cleanup ends + // up calling back to LocalFrameClient via WindowProxy. + GetScriptController().ClearForClose(); ++ // This is the earliest that scripting can be disabled: ++ // - FrameLoader::Detach() can fire XHR abort events ++ // - Document::Shutdown() can dispose plugins which can run script. ++ ScriptForbiddenScope forbid_script; + + // TODO(crbug.com/729196): Trace why LocalFrameView::DetachFromLayout crashes. + CHECK(!view_->IsAttached()); diff --git a/patches/common/chromium/blink_world_context.patch b/patches/common/chromium/blink_world_context.patch new file mode 100644 index 00000000000..3a36d4b4fa4 --- /dev/null +++ b/patches/common/chromium/blink_world_context.patch @@ -0,0 +1,45 @@ +diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc +index a93834fbe86e..937b7f335693 100644 +--- a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc ++++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc +@@ -843,6 +843,13 @@ v8::Local WebLocalFrameImpl::GlobalProxy() const { + return MainWorldScriptContext()->Global(); + } + ++v8::Local WebLocalFrameImpl::WorldScriptContext( ++ v8::Isolate* isolate, int world_id) const { ++ scoped_refptr world = DOMWrapperWorld::EnsureIsolatedWorld( ++ isolate, world_id); ++ return ToScriptState(GetFrame(), *world)->GetContext(); ++} ++ + bool WebFrame::ScriptCanAccess(WebFrame* target) { + return BindingSecurity::ShouldAllowAccessToFrame( + CurrentDOMWindow(V8PerIsolateData::MainThreadIsolate()), +diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.h b/third_party/blink/renderer/core/frame/web_local_frame_impl.h +index d66499296ff8..bfea68983fda 100644 +--- a/third_party/blink/renderer/core/frame/web_local_frame_impl.h ++++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.h +@@ -142,6 +142,8 @@ class CORE_EXPORT WebLocalFrameImpl final + int argc, + v8::Local argv[]) override; + v8::Local MainWorldScriptContext() const override; ++ v8::Local WorldScriptContext( ++ v8::Isolate* isolate, int world_id) const override; + v8::Local GlobalProxy() const override; + void Reload(WebFrameLoadType) override; + void ReloadWithOverrideURL(const WebURL& override_url, +diff --git a/third_party/blink/public/web/web_local_frame.h b/third_party/blink/public/web/web_local_frame.h +index ad0fa84f9511..69f96587b1f1 100644 +--- a/third_party/blink/public/web/web_local_frame.h ++++ b/third_party/blink/public/web/web_local_frame.h +@@ -404,6 +404,9 @@ class WebLocalFrame : public WebFrame { + // be calling this API. + virtual v8::Local MainWorldScriptContext() const = 0; + ++ virtual v8::Local WorldScriptContext( ++ v8::Isolate* isolate, int world_id) const = 0; ++ + // Executes script in the context of the current page and returns the value + // that the script evaluated to with callback. Script execution can be + // suspend. diff --git a/patches/common/chromium/boringssl_build_gn.patch b/patches/common/chromium/boringssl_build_gn.patch new file mode 100644 index 00000000000..1b3e7d69ee6 --- /dev/null +++ b/patches/common/chromium/boringssl_build_gn.patch @@ -0,0 +1,18 @@ +diff --git a/third_party/boringssl/BUILD.gn b/third_party/boringssl/BUILD.gn +index c75fb7c2bb7e..423f4b2ddb10 100644 +--- a/third_party/boringssl/BUILD.gn ++++ b/third_party/boringssl/BUILD.gn +@@ -44,6 +44,13 @@ config("no_asm_config") { + } + + all_sources = crypto_sources + ssl_sources ++if (is_electron_build) { ++ # Needed to build a nodejs-compatible boringssl. ++ all_sources += [ ++ "src/decrepit/evp/evp_do_all.c", ++ "src/decrepit/xts/xts.c", ++ ] ++} + + # Windows' assembly is built with Yasm. The other platforms use the platform + # assembler. diff --git a/patches/common/chromium/browser_compositor_mac.patch b/patches/common/chromium/browser_compositor_mac.patch new file mode 100644 index 00000000000..006862310b5 --- /dev/null +++ b/patches/common/chromium/browser_compositor_mac.patch @@ -0,0 +1,35 @@ +diff --git a/content/browser/renderer_host/browser_compositor_view_mac.h b/content/browser/renderer_host/browser_compositor_view_mac.h +index 7426062f7381..bd5cd2fcd230 100644 +--- a/content/browser/renderer_host/browser_compositor_view_mac.h ++++ b/content/browser/renderer_host/browser_compositor_view_mac.h +@@ -54,10 +54,13 @@ class CONTENT_EXPORT BrowserCompositorMac : public DelegatedFrameHostClient { + // These will not return nullptr until Destroy is called. + DelegatedFrameHost* GetDelegatedFrameHost(); + ++ ui::Layer* GetRootLayer() { return root_layer_.get(); } ++ + // Ensure that the currect compositor frame be cleared (even if it is + // potentially visible). + void ClearCompositorFrame(); + ++ ui::Compositor* GetCompositor(); + gfx::AcceleratedWidget GetAcceleratedWidget(); + void DidCreateNewRendererCompositorFrameSink( + viz::mojom::CompositorFrameSinkClient* renderer_compositor_frame_sink); +diff --git a/content/browser/renderer_host/browser_compositor_view_mac.mm b/content/browser/renderer_host/browser_compositor_view_mac.mm +index 7fcc24c15c37..7c31977b20f9 100644 +--- a/content/browser/renderer_host/browser_compositor_view_mac.mm ++++ b/content/browser/renderer_host/browser_compositor_view_mac.mm +@@ -208,6 +208,12 @@ BrowserCompositorMac::~BrowserCompositorMac() { + g_spare_recyclable_compositors.Get().clear(); + } + ++ui::Compositor* BrowserCompositorMac::GetCompositor() { ++ if (recyclable_compositor_) ++ return recyclable_compositor_->compositor(); ++ return nullptr; ++} ++ + gfx::AcceleratedWidget BrowserCompositorMac::GetAcceleratedWidget() { + if (recyclable_compositor_) { + return recyclable_compositor_->accelerated_widget_mac() diff --git a/patches/common/chromium/browser_plugin_guest.patch b/patches/common/chromium/browser_plugin_guest.patch new file mode 100644 index 00000000000..f297907afa7 --- /dev/null +++ b/patches/common/chromium/browser_plugin_guest.patch @@ -0,0 +1,18 @@ +diff --git a/content/browser/browser_plugin/browser_plugin_guest.cc b/content/browser/browser_plugin/browser_plugin_guest.cc +index 964c9a093a3b..f3b3d66ff267 100644 +--- a/content/browser/browser_plugin/browser_plugin_guest.cc ++++ b/content/browser/browser_plugin/browser_plugin_guest.cc +@@ -214,8 +214,11 @@ void BrowserPluginGuest::Init() { + + WebContentsImpl* owner_web_contents = static_cast( + delegate_->GetOwnerWebContents()); +- owner_web_contents->CreateBrowserPluginEmbedderIfNecessary(); +- InitInternal(BrowserPluginHostMsg_Attach_Params(), owner_web_contents); ++ if (nullptr != owner_web_contents) ++ { ++ owner_web_contents->CreateBrowserPluginEmbedderIfNecessary(); ++ InitInternal(BrowserPluginHostMsg_Attach_Params(), owner_web_contents); ++ } + } + + base::WeakPtr BrowserPluginGuest::AsWeakPtr() { diff --git a/patches/common/chromium/browser_plugin_wheel.patch b/patches/common/chromium/browser_plugin_wheel.patch new file mode 100644 index 00000000000..00f6f1658bd --- /dev/null +++ b/patches/common/chromium/browser_plugin_wheel.patch @@ -0,0 +1,25 @@ +diff --git a/content/renderer/browser_plugin/browser_plugin.cc b/content/renderer/browser_plugin/browser_plugin.cc +index 06762fb..e89b1f0 100644 +--- a/content/renderer/browser_plugin/browser_plugin.cc ++++ b/content/renderer/browser_plugin/browser_plugin.cc +@@ -448,15 +448,11 @@ blink::WebInputEventResult BrowserPlugin::handleInputEvent( + + DCHECK(!blink::WebInputEvent::IsTouchEventType(event.GetType())); + +- // With direct event routing turned on, BrowserPlugin should almost never +- // see wheel events any more. The two exceptions are (1) scroll bubbling, and +- // (2) synthetic mouse wheels generated by touchpad GesturePinch events on +- // Mac, which always go to the mainframe and thus may hit BrowserPlugin if +- // it's in a top-level embedder. In both cases we should indicate the event +- // as not handled (for GesturePinch on Mac, indicating the event has been +- // handled leads to touchpad pinch not working). +- if (event.GetType() == blink::WebInputEvent::kMouseWheel) +- return blink::WebInputEventResult::kNotHandled; ++ if (event.GetType() == blink::WebInputEvent::kMouseWheel) { ++ auto wheel_event = static_cast(event); ++ if (wheel_event.resending_plugin_id == browser_plugin_instance_id_) ++ return blink::WebInputEventResult::kNotHandled; ++ } + + if (blink::WebInputEvent::IsGestureEventType(event.GetType())) { + auto gesture_event = static_cast(event); diff --git a/patches/common/chromium/build_gn.patch b/patches/common/chromium/build_gn.patch new file mode 100644 index 00000000000..a789ec12432 --- /dev/null +++ b/patches/common/chromium/build_gn.patch @@ -0,0 +1,91 @@ +diff --git a/.gn b/.gn +index 50a8a2fe9f1e..66ced79f1627 100644 +--- a/.gn ++++ b/.gn +@@ -259,4 +259,8 @@ exec_script_whitelist = + # Not gypi-to-gn. + "//google_apis/BUILD.gn", + "//printing/BUILD.gn", ++ # While electron transitions to GN, we use gypi_to_gn to synchronize ++ # file lists ++ "//electron/BUILD.gn", ++ "//electron/brightray/BUILD.gn", + ] +diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn +index 7d60dd920904..d2f2cbc99915 100644 +--- a/build/config/BUILDCONFIG.gn ++++ b/build/config/BUILDCONFIG.gn +@@ -123,6 +123,10 @@ if (current_os == "") { + # even if the value is overridden, which is wasteful. See first bullet. + + declare_args() { ++ is_electron_build = false ++ is_electron_gn_build = false ++ is_mas_build = false ++ + # Set to enable the official build level of optimization. This has nothing + # to do with branding, but enables an additional level of optimization above + # release (!is_debug). This might be better expressed as a tri-state +@@ -539,6 +539,7 @@ default_compiler_configs = [ + "//build/config/compiler:thin_archive", + "//build/config/coverage:default_coverage", + "//build/config/sanitizers:default_sanitizer_flags", ++ "//electron/build/config:mas_build", + ] + + if (is_win) { +@@ -642,6 +645,7 @@ template("component") { + _component_mode = "shared_library" + } else if (defined(invoker.static_component_type)) { + assert(invoker.static_component_type == "static_library" || ++ (is_electron_build && invoker.static_component_type == "shared_library") || + invoker.static_component_type == "source_set") + _component_mode = invoker.static_component_type + } else if (is_android || !defined(invoker.sources)) { +diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn +index 9a10137aa405..bb33e5450eaa 100644 +--- a/build/config/compiler/BUILD.gn ++++ b/build/config/compiler/BUILD.gn +@@ -579,10 +579,13 @@ config("compiler") { + ldflags += [ "-Wl,--lto-O0" ] + } + +- cflags += [ "-fwhole-program-vtables" ] +- if (!is_win) { +- ldflags += [ "-fwhole-program-vtables" ] +- } ++ # -fwhole-program-vtables doesn't work well in Electron right now, as it's ++ # not a single binary and the optimizations break interfaces used across ++ # binary boundaries. ++ # cflags += [ "-fwhole-program-vtables" ] ++ # if (!is_win) { ++ # ldflags += [ "-fwhole-program-vtables" ] ++ #} + + # Work-around for http://openradar.appspot.com/20356002 + if (is_mac) { +diff --git a/build/config/win/BUILD.gn b/build/config/win/BUILD.gn +index 1f6bc13e087f..4630045ff554 100644 +--- a/build/config/win/BUILD.gn ++++ b/build/config/win/BUILD.gn +@@ -314,7 +314,7 @@ config("cfi_linker") { + # See https://msdn.microsoft.com/en-us/library/2kzt1wy3.aspx for a reference of + # what each value does. + config("default_crt") { +- if (is_component_build) { ++ if (is_component_build || (is_electron_build && !is_electron_gn_build)) { + # Component mode: dynamic CRT. Since the library is shared, it requires + # exceptions or will give errors about things not matching, so keep + # exceptions on. +diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn +index bc9fe2cc2000..9173f6f0324c 100644 +--- a/third_party/blink/renderer/platform/BUILD.gn ++++ b/third_party/blink/renderer/platform/BUILD.gn +@@ -134,6 +134,7 @@ action("instrumentation_probes") { + } + + executable("character_data_generator") { ++ configs += [ "//electron/build/config:build_time_executable" ] + sources = [ + "text/character_property_data_generator.cc", + "text/character_property_data_generator.h", diff --git a/patches/common/chromium/build_toolchain_win_patch.patch b/patches/common/chromium/build_toolchain_win_patch.patch new file mode 100644 index 00000000000..6d3aee2c684 --- /dev/null +++ b/patches/common/chromium/build_toolchain_win_patch.patch @@ -0,0 +1,60 @@ +diff --git a/build/toolchain/win/BUILD.gn b/build/toolchain/win/BUILD.gn +index 53f767a0bddb..661466b779e8 100644 +--- a/build/toolchain/win/BUILD.gn ++++ b/build/toolchain/win/BUILD.gn +@@ -176,6 +176,12 @@ template("msvc_toolchain") { + ] + + command = "$env_wrapper$cl /nologo /showIncludes ${clflags} $sys_include_flags{{defines}} {{include_dirs}} {{cflags}} {{cflags_c}} /c {{source}} /Fo{{output}} /Fd\"$pdbname\"" ++ ++ if (is_electron_build && !is_component_build) { ++ pdbdir = "{{target_out_dir}}" ++ pdbname = "{{label_name}}_c.pdb" ++ command = "$python_path $tool_wrapper_path cl-wrapper $env_wrapper$cl /nologo /showIncludes ${clflags} $sys_include_flags{{defines}} {{include_dirs}} {{cflags}} {{cflags_c}} /c {{source}} /Fo{{output}} $pdbdir \"$pdbname\"" ++ } + } + + tool("cxx") { +@@ -192,6 +198,12 @@ template("msvc_toolchain") { + ] + + command = "$env_wrapper$cl /nologo /showIncludes ${clflags} $sys_include_flags{{defines}} {{include_dirs}} {{cflags}} {{cflags_cc}} /c {{source}} /Fo{{output}} /Fd\"$pdbname\"" ++ ++ if (is_electron_build && !is_component_build) { ++ pdbdir = "{{target_out_dir}}" ++ pdbname = "{{label_name}}_cc.pdb" ++ command = "$python_path $tool_wrapper_path cl-wrapper $env_wrapper$cl /nologo /showIncludes ${clflags} $sys_include_flags{{defines}} {{include_dirs}} {{cflags}} {{cflags_cc}} /c {{source}} /Fo{{output}} $pdbdir \"$pdbname\"" ++ } + } + + tool("rc") { +diff --git a/build/toolchain/win/tool_wrapper.py b/build/toolchain/win/tool_wrapper.py +index 3a81368f3469..7c5ef1ea5db4 100644 +--- a/build/toolchain/win/tool_wrapper.py ++++ b/build/toolchain/win/tool_wrapper.py +@@ -315,6 +315,25 @@ class WinTool(object): + dirname = dirname[0] if dirname else None + return subprocess.call(args, shell=True, env=env, cwd=dirname) + ++ def ExecClWrapper(self, *args): ++ """Invokes cl.exe to compile a C/C++ source file.""" ++ args = list(args) ++ # Incorporate the PDB output dir into the PDB name to ensure the PDB name ++ # is unique (see https://github.com/electron/libchromiumcontent/issues/287) ++ pdb_name = args.pop() ++ pdb_dir = args.pop() ++ pdb_filename = '%s/%s_%s' % (pdb_dir, pdb_dir.replace('/', '_'), pdb_name) ++ # On Windows when args is a sequence instead of a single string ++ # subprocess.call() will use subprocess.list2cmdline() to convert the ++ # sequence to a string. Unfortunately the double-quote escaping done by ++ # subprocess.list2cmdline() mangles the /Fd"path/to/some.pdb" arg to ++ # /Fd\"path/to/some.pdb\", and cl.exe then fails to parse the PDB filename ++ # correctly. To work around this we use subprocess.list2cmdline() ++ # (even though it's not part of the public API) to construct most of the ++ # command line, and then append the /Fd flag. ++ pdb_flag = '/Fd"%s"' % pdb_filename ++ cmdline = '%s %s' % (subprocess.list2cmdline(args), pdb_flag) ++ return subprocess.call(cmdline, shell=False) + + if __name__ == '__main__': + sys.exit(main(sys.argv[1:])) diff --git a/patches/common/chromium/can_create_window.patch b/patches/common/chromium/can_create_window.patch new file mode 100644 index 00000000000..a7f3a09dfa0 --- /dev/null +++ b/patches/common/chromium/can_create_window.patch @@ -0,0 +1,235 @@ +diff --git a/content/browser/frame_host/render_frame_host_impl.cc b/content/browser/frame_host/render_frame_host_impl.cc +index 25841d376bcd..df41213f4c49 100644 +--- a/content/browser/frame_host/render_frame_host_impl.cc ++++ b/content/browser/frame_host/render_frame_host_impl.cc +@@ -2874,6 +2874,38 @@ void RenderFrameHostImpl::CreateNewWindow( + "frame_tree_node", frame_tree_node_->frame_tree_node_id(), "url", + params->target_url.possibly_invalid_spec()); + ++ scoped_refptr body; ++ if (params->body->has_object) { ++ body = new network::ResourceRequestBody; ++ std::vector elements; ++ for (const auto& iter : params->body->elements) { ++ network::DataElement element; ++ switch (iter->type) { ++ case network::DataElement::TYPE_BYTES: { ++ element.SetToBytes(iter->bytes.data(), iter->bytes.length()); ++ break; ++ } ++ case network::DataElement::TYPE_FILE: { ++ element.SetToFilePathRange(iter->path, iter->offset, iter->length, ++ iter->expected_modification_time); ++ break; ++ } ++ case network::DataElement::TYPE_BLOB: { ++ element.SetToBlobRange(iter->blob_uuid, iter->offset, iter->length); ++ break; ++ } ++ case network::DataElement::TYPE_DATA_PIPE: ++ default: ++ NOTREACHED(); ++ break; ++ } ++ elements.push_back(std::move(element)); ++ } ++ body->swap_elements(&elements); ++ body->set_identifier(params->body->identifier); ++ body->set_contains_sensitive_info(params->body->contains_sensitive_info); ++ } ++ + bool no_javascript_access = false; + + // Filter out URLs to which navigation is disallowed from this context. +@@ -2896,8 +2928,9 @@ void RenderFrameHostImpl::CreateNewWindow( + frame_tree_node_->frame_tree()->GetMainFrame()->GetLastCommittedURL(), + last_committed_origin_.GetURL(), params->window_container_type, + params->target_url, params->referrer, params->frame_name, +- params->disposition, *params->features, params->user_gesture, +- params->opener_suppressed, &no_javascript_access); ++ params->disposition, *params->features, params->additional_features, ++ body, params->user_gesture, params->opener_suppressed, ++ &no_javascript_access); + + if (!can_create_window) { + std::move(callback).Run(mojom::CreateNewWindowStatus::kIgnore, nullptr); +diff --git a/content/common/frame.mojom b/content/common/frame.mojom +index 99ec7e8d7995..26a4040fba97 100644 +--- a/content/common/frame.mojom ++++ b/content/common/frame.mojom +@@ -11,6 +11,8 @@ import "content/public/common/resource_type.mojom"; + import "content/public/common/resource_load_info.mojom"; + import "content/public/common/transferrable_url_loader.mojom"; + import "content/public/common/window_container_type.mojom"; ++import "mojo/public/mojom/base/file_path.mojom"; ++import "mojo/public/mojom/base/time.mojom"; + import "mojo/public/mojom/base/string16.mojom"; + import "mojo/public/mojom/base/unguessable_token.mojom"; + import "services/network/public/mojom/url_loader.mojom"; +@@ -146,6 +148,24 @@ interface FrameFactory { + CreateFrame(int32 frame_routing_id, Frame& frame); + }; + ++struct DataElement { ++ int32 type; ++ int64 length; ++ string bytes; ++ mojo_base.mojom.FilePath path; ++ int64 offset; ++ mojo_base.mojom.Time expected_modification_time; ++ url.mojom.Url filesystem_url; ++ string blob_uuid; ++}; ++ ++struct ResourceRequestBody { ++ bool has_object; ++ int64 identifier; ++ bool contains_sensitive_info; ++ array elements; ++}; ++ + struct CreateNewWindowParams { + // True if this open request came in the context of a user gesture. + bool user_gesture; +@@ -182,6 +202,10 @@ struct CreateNewWindowParams { + + // The window features to use for the new window. + blink.mojom.WindowFeatures features; ++ ++ // Extra fields added by Electron. ++ array additional_features; ++ ResourceRequestBody body; + }; + + // Operation result when the renderer asks the browser to create a new window. +diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc +index 37e2d88e28e9..6c366435ddd8 100644 +--- a/content/public/browser/content_browser_client.cc ++++ b/content/public/browser/content_browser_client.cc +@@ -382,6 +382,8 @@ bool ContentBrowserClient::CanCreateWindow( + const std::string& frame_name, + WindowOpenDisposition disposition, + const blink::mojom::WindowFeatures& features, ++ const std::vector& additional_features, ++ const scoped_refptr& body, + bool user_gesture, + bool opener_suppressed, + bool* no_javascript_access) { +diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h +index 63cb3851db0a..4a96c8851df0 100644 +--- a/content/public/browser/content_browser_client.h ++++ b/content/public/browser/content_browser_client.h +@@ -151,6 +151,7 @@ class RenderFrameHost; + class RenderProcessHost; + class RenderViewHost; + class ResourceContext; ++class ResourceRequestBody; + class SiteInstance; + class SpeechRecognitionManagerDelegate; + class StoragePartition; +@@ -625,6 +626,8 @@ class CONTENT_EXPORT ContentBrowserClient { + const std::string& frame_name, + WindowOpenDisposition disposition, + const blink::mojom::WindowFeatures& features, ++ const std::vector& additional_features, ++ const scoped_refptr& body, + bool user_gesture, + bool opener_suppressed, + bool* no_javascript_access); +diff --git a/content/renderer/render_view_impl.cc b/content/renderer/render_view_impl.cc +index 7a866ded50f1..f019ce3b24bb 100644 +--- a/content/renderer/render_view_impl.cc ++++ b/content/renderer/render_view_impl.cc +@@ -79,6 +79,7 @@ + #include "content/renderer/input/input_handler_manager.h" + #include "content/renderer/internal_document_state_data.h" + #include "content/renderer/loader/request_extra_data.h" ++#include "content/renderer/loader/web_url_request_util.h" + #include "content/renderer/media/audio_device_factory.h" + #include "content/renderer/media/stream/media_stream_device_observer.h" + #include "content/renderer/media/video_capture_impl_manager.h" +@@ -1258,6 +1259,46 @@ WebView* RenderViewImpl::CreateView(WebLocalFrame* creator, + } + params->features = ConvertWebWindowFeaturesToMojoWindowFeatures(features); + ++ params->body = mojom::ResourceRequestBody::New(); ++ auto body = GetRequestBodyForWebURLRequest(request); ++ if (body) { ++ params->body->has_object = true; ++ params->body->identifier = body->identifier(); ++ params->body->contains_sensitive_info = body->contains_sensitive_info(); ++ for (const auto& element : *body->elements()) { ++ content::mojom::DataElementPtr ptr = content::mojom::DataElement::New(); ++ ptr->type = element.type(); ++ switch (element.type()) { ++ case network::DataElement::TYPE_BYTES: { ++ ptr->bytes = std::string(element.bytes(), element.length()); ++ break; ++ } ++ case network::DataElement::TYPE_FILE: { ++ ptr->path = element.path(); ++ ptr->offset = element.offset(); ++ ptr->length = element.length(); ++ ptr->expected_modification_time = element.expected_modification_time(); ++ break; ++ } ++ case network::DataElement::TYPE_BLOB: { ++ ptr->blob_uuid = element.blob_uuid(); ++ ptr->offset = element.offset(); ++ ptr->length = element.length(); ++ break; ++ } ++ case network::DataElement::TYPE_CHUNKED_DATA_PIPE: ++ case network::DataElement::TYPE_RAW_FILE: ++ case network::DataElement::TYPE_DATA_PIPE: ++ case network::DataElement::TYPE_UNKNOWN: ++ NOTREACHED(); ++ break; ++ } ++ params->body->elements.push_back(std::move(ptr)); ++ } ++ } else { ++ params->body->has_object = false; ++ } ++ + // We preserve this information before sending the message since |params| is + // moved on send. + bool is_background_tab = +diff --git a/content/browser/security_exploit_browsertest.cc b/content/browser/security_exploit_browsertest.cc +index 0a1f363a673a..adcef6fca779 100644 +--- a/content/browser/security_exploit_browsertest.cc ++++ b/content/browser/security_exploit_browsertest.cc +@@ -293,6 +293,7 @@ IN_PROC_BROWSER_TEST_F(SecurityExploitBrowserTest, + + mojom::CreateNewWindowParamsPtr params = mojom::CreateNewWindowParams::New(); + params->target_url = GURL("about:blank"); ++ params->body = mojom::ResourceRequestBody::New(); + pending_rfh->CreateNewWindow( + std::move(params), base::BindOnce([](mojom::CreateNewWindowStatus, + mojom::CreateNewWindowReplyPtr) {})); +diff --git a/content/shell/browser/layout_test/layout_test_content_browser_client.cc b/content/shell/browser/layout_test/layout_test_content_browser_client.cc +index 2eaee37ec780..9994df95a798 100644 +--- a/content/shell/browser/layout_test/layout_test_content_browser_client.cc ++++ b/content/shell/browser/layout_test/layout_test_content_browser_client.cc +@@ -182,6 +182,8 @@ bool LayoutTestContentBrowserClient::CanCreateWindow( + const std::string& frame_name, + WindowOpenDisposition disposition, + const blink::mojom::WindowFeatures& features, ++ const std::vector& additional_features, ++ const scoped_refptr& body, + bool user_gesture, + bool opener_suppressed, + bool* no_javascript_access) { +diff --git a/content/shell/browser/layout_test/layout_test_content_browser_client.h b/content/shell/browser/layout_test/layout_test_content_browser_client.h +index 62b637bc80ce..1a9a06ce4bf6 100644 +--- a/content/shell/browser/layout_test/layout_test_content_browser_client.h ++++ b/content/shell/browser/layout_test/layout_test_content_browser_client.h +@@ -58,6 +58,8 @@ class LayoutTestContentBrowserClient : public ShellContentBrowserClient { + const std::string& frame_name, + WindowOpenDisposition disposition, + const blink::mojom::WindowFeatures& features, ++ const std::vector& additional_features, ++ const scoped_refptr& body, + bool user_gesture, + bool opener_suppressed, + bool* no_javascript_access) override; diff --git a/patches/common/chromium/chrome_key_systems.patch b/patches/common/chromium/chrome_key_systems.patch new file mode 100644 index 00000000000..5cb1d8db399 --- /dev/null +++ b/patches/common/chromium/chrome_key_systems.patch @@ -0,0 +1,29 @@ +diff --git a/chrome/renderer/media/chrome_key_systems.cc b/chrome/renderer/media/chrome_key_systems.cc +index f3033337199b..856bc8f0b143 100644 +--- a/chrome/renderer/media/chrome_key_systems.cc ++++ b/chrome/renderer/media/chrome_key_systems.cc +@@ -14,7 +14,9 @@ + #include "base/strings/string_split.h" + #include "base/strings/utf_string_conversions.h" + #include "build/build_config.h" ++#if 0 + #include "chrome/renderer/chrome_render_thread_observer.h" ++#endif + #include "components/cdm/renderer/external_clear_key_key_system_properties.h" + #include "components/cdm/renderer/widevine_key_system_properties.h" + #include "content/public/renderer/render_thread.h" +@@ -140,12 +142,14 @@ static void AddExternalClearKey( + #if defined(WIDEVINE_CDM_AVAILABLE) + // Returns persistent-license session support. + EmeSessionTypeSupport GetPersistentLicenseSupport(bool supported_by_the_cdm) { ++#if 0 + // Do not support persistent-license if the process cannot persist data. + // TODO(crbug.com/457487): Have a better plan on this. See bug for details. + if (ChromeRenderThreadObserver::is_incognito_process()) { + DVLOG(2) << __func__ << ": Not supported in incognito process."; + return EmeSessionTypeSupport::NOT_SUPPORTED; + } ++#endif + + if (!supported_by_the_cdm) { + DVLOG(2) << __func__ << ": Not supported by the CDM."; diff --git a/patches/common/chromium/compositor_delegate.patch b/patches/common/chromium/compositor_delegate.patch new file mode 100644 index 00000000000..c606c4faaad --- /dev/null +++ b/patches/common/chromium/compositor_delegate.patch @@ -0,0 +1,72 @@ +diff --git a/content/browser/compositor/gpu_process_transport_factory.cc b/content/browser/compositor/gpu_process_transport_factory.cc +index 7b9fc4114c52..bdbbf93f6f0d 100644 +--- a/content/browser/compositor/gpu_process_transport_factory.cc ++++ b/content/browser/compositor/gpu_process_transport_factory.cc +@@ -495,9 +495,19 @@ void GpuProcessTransportFactory::EstablishedGpuChannel( + // surfaces as they are not following the correct mode. + DisableGpuCompositing(compositor.get()); + } ++ ++ std::unique_ptr output_device; ++ if (compositor->delegate()) { ++ output_device = compositor->delegate()->CreateSoftwareOutputDevice( ++ compositor.get()); ++ } ++ if (!output_device) { ++ output_device = CreateSoftwareOutputDevice(compositor->widget()); ++ } ++ + display_output_surface = + std::make_unique( +- CreateSoftwareOutputDevice(compositor->widget()), ++ std::move(output_device), + std::move(vsync_callback), compositor->task_runner()); + } else { + DCHECK(context_provider); +diff --git a/ui/compositor/compositor.h b/ui/compositor/compositor.h +index d842aa55175b..2c2131774b71 100644 +--- a/ui/compositor/compositor.h ++++ b/ui/compositor/compositor.h +@@ -24,6 +24,7 @@ + #include "components/viz/common/surfaces/frame_sink_id.h" + #include "components/viz/common/surfaces/local_surface_id.h" + #include "components/viz/host/host_frame_sink_client.h" ++#include "components/viz/service/display/software_output_device.h" + #include "third_party/skia/include/core/SkColor.h" + #include "third_party/skia/include/core/SkMatrix44.h" + #include "ui/compositor/compositor_animation_observer.h" +@@ -182,6 +183,15 @@ class COMPOSITOR_EXPORT ContextFactory { + virtual void RemoveObserver(ContextFactoryObserver* observer) = 0; + }; + ++class COMPOSITOR_EXPORT CompositorDelegate { ++ public: ++ virtual std::unique_ptr CreateSoftwareOutputDevice( ++ ui::Compositor* compositor) = 0; ++ ++ protected: ++ virtual ~CompositorDelegate() {} ++}; ++ + // Compositor object to take care of GPU painting. + // A Browser compositor object is responsible for generating the final + // displayable form of pixels comprising a single widget's contents. It draws an +@@ -221,6 +231,9 @@ class COMPOSITOR_EXPORT Compositor : public cc::LayerTreeHostClient, + // Schedules a redraw of the layer tree associated with this compositor. + void ScheduleDraw(); + ++ CompositorDelegate* delegate() const { return delegate_; } ++ void SetDelegate(CompositorDelegate* delegate) { delegate_ = delegate; } ++ + // Sets the root of the layer tree drawn by this Compositor. The root layer + // must have no parent. The compositor's root layer is reset if the root layer + // is destroyed. NULL can be passed to reset the root layer, in which case the +@@ -426,6 +439,8 @@ class COMPOSITOR_EXPORT Compositor : public cc::LayerTreeHostClient, + ui::ContextFactory* context_factory_; + ui::ContextFactoryPrivate* context_factory_private_; + ++ CompositorDelegate* delegate_ = nullptr; ++ + // The root of the Layer tree drawn by this compositor. + Layer* root_layer_ = nullptr; + diff --git a/patches/common/chromium/content_browser_manifest.patch b/patches/common/chromium/content_browser_manifest.patch new file mode 100644 index 00000000000..65d517ec1ba --- /dev/null +++ b/patches/common/chromium/content_browser_manifest.patch @@ -0,0 +1,12 @@ +diff --git a/content/public/app/mojo/content_browser_manifest.json b/content/public/app/mojo/content_browser_manifest.json +index 5a217fa9b741..8fd1b39ea6ca 100644 +--- a/content/public/app/mojo/content_browser_manifest.json ++++ b/content/public/app/mojo/content_browser_manifest.json +@@ -82,6 +82,7 @@ + "device:battery_monitor", + "device:generic_sensor", + "device:geolocation", ++ "device:geolocation_control", + "device:hid", + "device:input_service", + "device:nfc", diff --git a/patches/common/chromium/crashpad-disabled-windows.patch b/patches/common/chromium/crashpad-disabled-windows.patch new file mode 100644 index 00000000000..b38a9b1bdb0 --- /dev/null +++ b/patches/common/chromium/crashpad-disabled-windows.patch @@ -0,0 +1,48 @@ +diff --git a/components/crash/core/common/BUILD.gn b/components/crash/core/common/BUILD.gn +index 4f67529f5c9a..a41bdf709d99 100644 +--- a/components/crash/core/common/BUILD.gn ++++ b/components/crash/core/common/BUILD.gn +@@ -13,7 +13,7 @@ group("common") { + } + } + +-use_crashpad = is_mac || is_win ++use_crashpad = is_mac + use_stubs = is_fuchsia + + # Crashpad's annotation system can store data on a per-module basis (i.e., +@@ -128,7 +128,7 @@ source_set("unit_tests") { + sources += [ "objc_zombie_unittest.mm" ] + } + +- if (!is_mac && !is_win && !is_fuchsia) { ++ if (!is_mac && !is_fuchsia) { + include_dirs = [ "//third_party/breakpad/breakpad/src/" ] + sources += [ "crash_key_breakpad_unittest.cc" ] + } +diff --git a/components/crash/core/common/crash_key.h b/components/crash/core/common/crash_key.h +index 951c7e941962..bdf6bb40e1fb 100644 +--- a/components/crash/core/common/crash_key.h ++++ b/components/crash/core/common/crash_key.h +@@ -19,7 +19,7 @@ + // Annotation interface. Because not all platforms use Crashpad yet, a + // source-compatible interface is provided on top of the older Breakpad + // storage mechanism. +-#if (defined(OS_MACOSX) && !defined(OS_IOS)) || defined(OS_WIN) ++#if (defined(OS_MACOSX) && !defined(OS_IOS)) + #define USE_CRASHPAD_ANNOTATION 1 + #endif + +diff --git a/components/crash/core/common/crash_key_breakpad.cc b/components/crash/core/common/crash_key_breakpad.cc +index 0351e01fa18f..1c355bd89844 100644 +--- a/components/crash/core/common/crash_key_breakpad.cc ++++ b/components/crash/core/common/crash_key_breakpad.cc +@@ -15,7 +15,7 @@ + #include "components/crash/core/common/crash_key_base_support.h" + #include "components/crash/core/common/crash_key_internal.h" + +-#if defined(OS_MACOSX) || defined(OS_IOS) || defined(OS_WIN) ++#if defined(OS_MACOSX) || defined(OS_IOS) + #error "This file should not be used when Crashpad is available, nor on iOS." + #endif + diff --git a/patches/common/chromium/dcheck.patch b/patches/common/chromium/dcheck.patch new file mode 100644 index 00000000000..09d6d672f83 --- /dev/null +++ b/patches/common/chromium/dcheck.patch @@ -0,0 +1,272 @@ +diff --git a/base/logging.h b/base/logging.h +index 582fb89868cd..24d3e82232b6 100644 +--- a/base/logging.h ++++ b/base/logging.h +@@ -850,7 +850,7 @@ const LogSeverity LOG_DCHECK = LOG_INFO; + + #else // !(defined(_PREFAST_) && defined(OS_WIN)) + +-#if DCHECK_IS_ON() ++#if DCHECK_IS_ON() && !defined(ELECTRON_NO_DCHECK) + + #define DCHECK(condition) \ + LAZY_STREAM(LOG_STREAM(DCHECK), !ANALYZER_ASSUME_TRUE(condition)) \ +diff --git a/base/memory/weak_ptr.cc b/base/memory/weak_ptr.cc +index 8879651e6da7..33fe8948a063 100644 +--- a/base/memory/weak_ptr.cc ++++ b/base/memory/weak_ptr.cc +@@ -23,8 +23,8 @@ void WeakReference::Flag::Invalidate() { + } + + bool WeakReference::Flag::IsValid() const { +- DCHECK(sequence_checker_.CalledOnValidSequence()) +- << "WeakPtrs must be checked on the same sequenced thread."; ++ // DCHECK(sequence_checker_.CalledOnValidSequence()) ++ // << "WeakPtrs must be checked on the same sequenced thread."; + return is_valid_; + } + +diff --git a/base/process/kill_win.cc b/base/process/kill_win.cc +index 6a0038e2c00d..dd00dfb3e5d0 100644 +--- a/base/process/kill_win.cc ++++ b/base/process/kill_win.cc +@@ -45,7 +45,7 @@ TerminationStatus GetTerminationStatus(ProcessHandle handle, int* exit_code) { + DWORD tmp_exit_code = 0; + + if (!::GetExitCodeProcess(handle, &tmp_exit_code)) { +- DPLOG(FATAL) << "GetExitCodeProcess() failed"; ++ // DPLOG(FATAL) << "GetExitCodeProcess() failed"; + + // This really is a random number. We haven't received any + // information about the exit code, presumably because this +diff --git a/components/viz/service/display/program_binding.h b/components/viz/service/display/program_binding.h +index 70f1ff97b1ac..d1abd804e988 100644 +--- a/components/viz/service/display/program_binding.h ++++ b/components/viz/service/display/program_binding.h +@@ -416,7 +416,7 @@ class VIZ_SERVICE_EXPORT Program : public ProgramBindingBase { + if (!ProgramBindingBase::Init(context_provider->ContextGL(), + vertex_shader_.GetShaderString(), + fragment_shader_.GetShaderString())) { +- DCHECK(IsContextLost(context_provider->ContextGL())); ++ // DCHECK(IsContextLost(context_provider->ContextGL())); + return; + } + +@@ -428,7 +428,7 @@ class VIZ_SERVICE_EXPORT Program : public ProgramBindingBase { + + // Link after binding uniforms + if (!Link(context_provider->ContextGL())) { +- DCHECK(IsContextLost(context_provider->ContextGL())); ++ // DCHECK(IsContextLost(context_provider->ContextGL())); + return; + } + +diff --git a/content/browser/frame_host/navigation_controller_impl.cc b/content/browser/frame_host/navigation_controller_impl.cc +index ff1d3fcb6eba..ad6578f645d4 100644 +--- a/content/browser/frame_host/navigation_controller_impl.cc ++++ b/content/browser/frame_host/navigation_controller_impl.cc +@@ -1079,8 +1079,10 @@ NavigationType NavigationControllerImpl::ClassifyNavigation( + return NAVIGATION_TYPE_NEW_SUBFRAME; + } + +- // We only clear the session history when navigating to a new page. +- DCHECK(!params.history_list_was_cleared); ++ // Electron does its own book keeping of navigation entries and we ++ // expect content to not track any, by clearing history list for ++ // all navigations. ++ // DCHECK(!params.history_list_was_cleared); + + if (rfh->GetParent()) { + // All manual subframes would be did_create_new_entry and handled above, so +@@ -1301,7 +1303,10 @@ void NavigationControllerImpl::RendererDidNavigateToNewPage( + new_entry->GetFavicon() = GetLastCommittedEntry()->GetFavicon(); + } + +- DCHECK(!params.history_list_was_cleared || !replace_entry); ++ // Electron does its own book keeping of navigation entries and we ++ // expect content to not track any, by clearing history list for ++ // all navigations. ++ // DCHECK(!params.history_list_was_cleared || !replace_entry); + // The browser requested to clear the session history when it initiated the + // navigation. Now we know that the renderer has updated its state accordingly + // and it is safe to also clear the browser side history. +diff --git a/content/browser/frame_host/render_frame_host_impl.cc b/content/browser/frame_host/render_frame_host_impl.cc +index 346765edaef9..a30e87bfcda6 100644 +--- a/content/browser/frame_host/render_frame_host_impl.cc ++++ b/content/browser/frame_host/render_frame_host_impl.cc +@@ -2072,8 +2073,10 @@ void RenderFrameHostImpl::AllowBindings(int bindings_flags) { + } + + enabled_bindings_ |= bindings_flags; +- if (GetParent()) +- DCHECK_EQ(GetParent()->GetEnabledBindings(), GetEnabledBindings()); ++ // WebUI in sub frames require binding policy while the parent does not, ++ // Fix this when we use OOPIF in Electron. ++ // if (GetParent()) ++ // DCHECK_EQ(GetParent()->GetEnabledBindings(), GetEnabledBindings()); + + if (render_frame_created_) { + if (!frame_bindings_control_) +diff --git a/content/browser/renderer_host/render_widget_host_view_cocoa.mm b/content/browser/renderer_host/render_widget_host_view_cocoa.mm +index 8ee84cdafbde..c7ad6fa8c75f 100644 +--- a/content/browser/renderer_host/render_widget_host_view_cocoa.mm ++++ b/content/browser/renderer_host/render_widget_host_view_cocoa.mm +@@ -618,8 +618,8 @@ void ExtractUnderlines(NSAttributedString* string, + if (EventIsReservedBySystem(theEvent)) + return; + +- DCHECK(eventType != NSKeyDown || +- !equiv == !(modifierFlags & NSCommandKeyMask)); ++ // DCHECK(eventType != NSKeyDown || ++ // !equiv == !(modifierFlags & NSCommandKeyMask)); + + if (eventType == NSFlagsChanged) { + // Ignore NSFlagsChanged events from the NumLock and Fn keys as +diff --git a/ppapi/host/ppapi_host.cc b/ppapi/host/ppapi_host.cc +index f3c68fab3de6..b8609daf3ef9 100644 +--- a/ppapi/host/ppapi_host.cc ++++ b/ppapi/host/ppapi_host.cc +@@ -240,7 +240,7 @@ void PpapiHost::OnHostMsgResourceCreated( + CreateResourceHost(params.pp_resource(), instance, nested_msg); + + if (!resource_host.get()) { +- NOTREACHED(); ++ // NOTREACHED(); + return; + } + +diff --git a/third_party/blink/renderer/core/loader/BUILD.gn b/third_party/blink/renderer/core/loader/BUILD.gn +index 82f6e8bc9d33..ccad95d61a4a 100644 +--- a/third_party/blink/renderer/core/loader/BUILD.gn ++++ b/third_party/blink/renderer/core/loader/BUILD.gn +@@ -129,4 +129,11 @@ blink_core_sources("loader") { + public_deps = [ + "//third_party/blink/renderer/platform", + ] ++ ++ if (is_electron_build) { ++ if (!defined(defines)) { ++ defines = [] ++ } ++ defines += [ "ELECTRON_NO_DCHECK" ] ++ } + } +diff --git a/third_party/blink/renderer/core/dom/node.cc b/third_party/blink/renderer/core/dom/node.cc +index 922a2561bcef..e31fa34f98ea 100644 +--- a/third_party/blink/renderer/core/dom/node.cc ++++ b/third_party/blink/renderer/core/dom/node.cc +@@ -2435,7 +2435,7 @@ StaticNodeList* Node::getDestinationInsertionPoints() { + + HTMLSlotElement* Node::AssignedSlot() const { + // assignedSlot doesn't need to call updateDistribution(). +- DCHECK(!IsPseudoElement()); ++ // DCHECK(!IsPseudoElement()); + if (ShadowRoot* root = V1ShadowRootOfParent()) + return root->AssignedSlotFor(*this); + return nullptr; +diff --git a/third_party/blink/renderer/platform/wtf/text/string_impl.h b/third_party/blink/renderer/platform/wtf/text/string_impl.h +index 158d81ca9ba2..1b6aafecadef 100644 +--- a/third_party/blink/renderer/platform/wtf/text/string_impl.h ++++ b/third_party/blink/renderer/platform/wtf/text/string_impl.h +@@ -258,21 +258,21 @@ class WTF_EXPORT StringImpl { + } + + ALWAYS_INLINE bool HasOneRef() const { +-#if DCHECK_IS_ON() ++#if 0 + DCHECK(IsStatic() || verifier_.IsSafeToUse()) << AsciiForDebugging(); + #endif + return ref_count_ == 1; + } + + ALWAYS_INLINE void AddRef() const { +-#if DCHECK_IS_ON() ++#if 0 + DCHECK(IsStatic() || verifier_.OnRef(ref_count_)) << AsciiForDebugging(); + #endif + ++ref_count_; + } + + ALWAYS_INLINE void Release() const { +-#if DCHECK_IS_ON() ++#if 0 + DCHECK(IsStatic() || verifier_.OnDeref(ref_count_)) + << AsciiForDebugging() << " " << CurrentThread(); + #endif +diff --git a/url/BUILD.gn b/url/BUILD.gn +index 82eb115ae666..b4806804cdbf 100644 +--- a/url/BUILD.gn ++++ b/url/BUILD.gn +@@ -96,6 +96,10 @@ component("url") { + ] + deps += [ "//third_party/icu" ] + } ++ ++ if (is_electron_build) { ++ defines += [ "ELECTRON_NO_DCHECK" ] ++ } + } + + if (is_android) { +diff --git a/ui/base/clipboard/clipboard_win.cc b/ui/base/clipboard/clipboard_win.cc +index 674b0e9a909c..a1bff6e40f56 100644 +--- a/ui/base/clipboard/clipboard_win.cc ++++ b/ui/base/clipboard/clipboard_win.cc +@@ -886,9 +886,9 @@ void ClipboardWin::WriteBitmapFromHandle(HBITMAP source_hbitmap, + } + + void ClipboardWin::WriteToClipboard(unsigned int format, HANDLE handle) { +- DCHECK(clipboard_owner_->hwnd() != NULL); ++ // DCHECK(clipboard_owner_->hwnd() != NULL); + if (handle && !::SetClipboardData(format, handle)) { +- DCHECK(ERROR_CLIPBOARD_NOT_OPEN != GetLastError()); ++ // DCHECK(ERROR_CLIPBOARD_NOT_OPEN != GetLastError()); + FreeData(format, handle); + } + } + diff --git a/third_party/WebKit/Source/core/animation/ElementAnimations.cpp b/third_party/WebKit/Source/core/animation/ElementAnimations.cpp + index 60b8123cd818..dc719dd31dbf 100644 + --- a/third_party/WebKit/Source/core/animation/ElementAnimations.cpp + +++ b/third_party/WebKit/Source/core/animation/ElementAnimations.cpp + @@ -108,7 +108,7 @@ void ElementAnimations::UpdateBaseComputedStyle( + base_computed_style_ = nullptr; + return; + } + -#if DCHECK_IS_ON() + +#if 0 + if (base_computed_style_ && computed_style) + DCHECK(*base_computed_style_ == *computed_style); + #endif +diff --git a/base/process/process_metrics_win.cc b/base/process/process_metrics_win.cc +index faabdbf63a2a..ba56e4cd994c 100644 +--- a/base/process/process_metrics_win.cc ++++ b/base/process/process_metrics_win.cc +@@ -179,10 +179,9 @@ bool ProcessMetrics::GetIOCounters(IoCounters* io_counters) const { + ProcessMetrics::ProcessMetrics(ProcessHandle process) : last_system_time_(0) { + if (process) { + HANDLE duplicate_handle = INVALID_HANDLE_VALUE; +- BOOL result = ::DuplicateHandle(::GetCurrentProcess(), process, +- ::GetCurrentProcess(), &duplicate_handle, +- PROCESS_QUERY_INFORMATION, FALSE, 0); +- DPCHECK(result); ++ ::DuplicateHandle(::GetCurrentProcess(), process, ++ ::GetCurrentProcess(), &duplicate_handle, ++ PROCESS_QUERY_INFORMATION, FALSE, 0); + process_.Set(duplicate_handle); + } + } +diff --git a/components/viz/service/display_embedder/server_shared_bitmap_manager.cc b/components/viz/service/display_embedder/server_shared_bitmap_manager.cc +index 9477a5aa45f9..895425c8c6cc 100644 +--- a/components/viz/service/display_embedder/server_shared_bitmap_manager.cc ++++ b/components/viz/service/display_embedder/server_shared_bitmap_manager.cc +@@ -69,7 +69,9 @@ base::LazyInstance::DestructorAtExit + ServerSharedBitmapManager::ServerSharedBitmapManager() = default; + + ServerSharedBitmapManager::~ServerSharedBitmapManager() { +- DCHECK(handle_map_.empty()); ++ // FIXME(alexeykuzmin): Gets constantly triggered on Windows CI. ++ // Backporting https://chromium-review.googlesource.com/802574 should help. ++ // DCHECK(handle_map_.empty()); + } + + ServerSharedBitmapManager* ServerSharedBitmapManager::current() { diff --git a/patches/common/chromium/desktop_screen_win.patch b/patches/common/chromium/desktop_screen_win.patch new file mode 100644 index 00000000000..df12ce0cba2 --- /dev/null +++ b/patches/common/chromium/desktop_screen_win.patch @@ -0,0 +1,13 @@ +diff --git a/ui/views/widget/desktop_aura/desktop_screen_win.cc b/ui/views/widget/desktop_aura/desktop_screen_win.cc +index f772f64..7d13f9f 100644 +--- a/ui/views/widget/desktop_aura/desktop_screen_win.cc ++++ b/ui/views/widget/desktop_aura/desktop_screen_win.cc +@@ -32,6 +32,8 @@ display::Display DesktopScreenWin::GetDisplayMatching( + } + + HWND DesktopScreenWin::GetHWNDFromNativeView(gfx::NativeView window) const { ++ if (!window) ++ return NULL; + aura::WindowTreeHost* host = window->GetHost(); + return host ? host->GetAcceleratedWidget() : NULL; + } diff --git a/patches/common/chromium/disable-recursive-surface-sync.patch b/patches/common/chromium/disable-recursive-surface-sync.patch new file mode 100644 index 00000000000..4a062f12f38 --- /dev/null +++ b/patches/common/chromium/disable-recursive-surface-sync.patch @@ -0,0 +1,16 @@ +diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc +index a9b9d180b0eb..5ad8b93114a7 100644 +--- a/content/browser/renderer_host/render_widget_host_impl.cc ++++ b/content/browser/renderer_host/render_widget_host_impl.cc +@@ -972,6 +975,11 @@ void RenderWidgetHostImpl::PauseForPendingResizeOrRepaints() { + if (is_hidden()) + return; + ++ // Do not pause if there is already a pending operation with the ++ // backing store. ++ if (in_get_backing_store_) ++ return; ++ + // Do not pause if there is not a paint or resize already coming. + if (!repaint_ack_pending_ && !resize_ack_pending_) + return; diff --git a/patches/common/chromium/disable-redraw-lock.patch b/patches/common/chromium/disable-redraw-lock.patch new file mode 100644 index 00000000000..4a4b2e89cdb --- /dev/null +++ b/patches/common/chromium/disable-redraw-lock.patch @@ -0,0 +1,60 @@ +diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc +index c8fb7eecb9c8..3d995aa331b1 100644 +--- a/ui/views/win/hwnd_message_handler.cc ++++ b/ui/views/win/hwnd_message_handler.cc +@@ -251,6 +251,10 @@ const int kSynthesizedMouseMessagesTimeDifference = 500; + + } // namespace + ++bool HWNDMessageHandlerDelegate::HasNativeFrame() const { ++ return false; ++} ++ + // A scoping class that prevents a window from being able to redraw in response + // to invalidations that may occur within it for the lifetime of the object. + // +@@ -302,6 +306,7 @@ class HWNDMessageHandler::ScopedRedrawLock { + cancel_unlock_(false), + should_lock_(owner_->IsVisible() && !owner->HasChildRenderingWindow() && + ::IsWindow(hwnd_) && ++ !owner_->HasNativeFrame() && + (!(GetWindowLong(hwnd_, GWL_STYLE) & WS_CAPTION) || + !ui::win::IsAeroGlassEnabled())) { + if (should_lock_) +@@ -903,6 +908,10 @@ bool HWNDMessageHandler::HasChildRenderingWindow() { + hwnd()); + } + ++bool HWNDMessageHandler::HasNativeFrame() { ++ return delegate_->HasNativeFrame(); ++} ++ + //////////////////////////////////////////////////////////////////////////////// + // HWNDMessageHandler, gfx::WindowImpl overrides: + +diff --git a/ui/views/win/hwnd_message_handler.h b/ui/views/win/hwnd_message_handler.h +index 5d5765c1928e..d77991cfa737 100644 +--- a/ui/views/win/hwnd_message_handler.h ++++ b/ui/views/win/hwnd_message_handler.h +@@ -227,6 +227,8 @@ class VIEWS_EXPORT HWNDMessageHandler : public gfx::WindowImpl, + typedef std::set TouchIDs; + enum class DwmFrameState { OFF, ON }; + ++ bool HasNativeFrame(); ++ + // Overridden from WindowImpl: + HICON GetDefaultWindowIcon() const override; + HICON GetSmallWindowIcon() const override; +diff --git a/ui/views/win/hwnd_message_handler_delegate.h b/ui/views/win/hwnd_message_handler_delegate.h +index d13f807e4a75..877189d63616 100644 +--- a/ui/views/win/hwnd_message_handler_delegate.h ++++ b/ui/views/win/hwnd_message_handler_delegate.h +@@ -46,6 +46,8 @@ class VIEWS_EXPORT HWNDMessageHandlerDelegate { + // True if the widget associated with this window has a non-client view. + virtual bool HasNonClientView() const = 0; + ++ virtual bool HasNativeFrame() const; ++ + // Returns who we want to be drawing the frame. Either the system (Windows) + // will handle it or Chrome will custom draw it. + virtual FrameMode GetFrameMode() const = 0; diff --git a/patches/common/chromium/disable_detach_webview_frame.patch b/patches/common/chromium/disable_detach_webview_frame.patch new file mode 100644 index 00000000000..a831d01dcb6 --- /dev/null +++ b/patches/common/chromium/disable_detach_webview_frame.patch @@ -0,0 +1,17 @@ +diff --git a/content/browser/frame_host/render_frame_proxy_host.cc b/content/browser/frame_host/render_frame_proxy_host.cc +index b44b0fd..a74d827 100644 +--- a/content/browser/frame_host/render_frame_proxy_host.cc ++++ b/content/browser/frame_host/render_frame_proxy_host.cc +@@ -253,6 +253,12 @@ void RenderFrameProxyHost::SetDestructionCallback( + + void RenderFrameProxyHost::OnDetach() { + if (frame_tree_node_->render_manager()->ForInnerDelegate()) { ++ // Don't detach the frame for webview, we will manage the WebContents ++ // manually. ++ // We should revisit this bug after upgrading to newer versions of Chrome, ++ // this patch was introduced in Chrome 66. ++ return; ++ + // Only main frame proxy can detach for inner WebContents. + DCHECK(frame_tree_node_->IsMainFrame()); + frame_tree_node_->render_manager()->RemoveOuterDelegateFrame(); diff --git a/patches/common/chromium/disable_hidden.patch b/patches/common/chromium/disable_hidden.patch new file mode 100644 index 00000000000..740a3507586 --- /dev/null +++ b/patches/common/chromium/disable_hidden.patch @@ -0,0 +1,28 @@ +diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc +index 77c870b8a075..f1c4076788c5 100644 +--- a/content/browser/renderer_host/render_widget_host_impl.cc ++++ b/content/browser/renderer_host/render_widget_host_impl.cc +@@ -664,6 +664,9 @@ void RenderWidgetHostImpl::WasHidden() { + if (is_hidden_) + return; + ++ if (disable_hidden_) ++ return; ++ + RejectMouseLockOrUnlockIfNecessary(); + + TRACE_EVENT0("renderer_host", "RenderWidgetHostImpl::WasHidden"); +diff --git a/content/browser/renderer_host/render_widget_host_impl.h b/content/browser/renderer_host/render_widget_host_impl.h +index b6aa99e..ef4fa35 100644 +--- a/content/browser/renderer_host/render_widget_host_impl.h ++++ b/content/browser/renderer_host/render_widget_host_impl.h +@@ -124,6 +124,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl : public RenderWidgetHost, + // RenderWidgetHostImpl. + static RenderWidgetHostImpl* From(RenderWidgetHost* rwh); + ++ // Electron: Prevents the widget from getting hidden. ++ bool disable_hidden_ = false; ++ + void set_hung_renderer_delay(const base::TimeDelta& delay) { + hung_renderer_delay_ = delay; + } diff --git a/patches/common/chromium/disable_scroll_begin_dcheck.patch b/patches/common/chromium/disable_scroll_begin_dcheck.patch new file mode 100644 index 00000000000..079e20c2e80 --- /dev/null +++ b/patches/common/chromium/disable_scroll_begin_dcheck.patch @@ -0,0 +1,28 @@ +diff --git a/content/browser/renderer_host/input/mouse_wheel_event_queue.cc b/content/browser/renderer_host/input/mouse_wheel_event_queue.cc +index 5d5bead..f2ac4d8 100644 +--- a/content/browser/renderer_host/input/mouse_wheel_event_queue.cc ++++ b/content/browser/renderer_host/input/mouse_wheel_event_queue.cc +@@ -339,7 +339,7 @@ void MouseWheelEventQueue::SendScrollBegin( + (synthetic && !needs_scroll_begin_when_scroll_latching_disabled_) || + needs_scroll_begin_when_scroll_latching_disabled_); + +- DCHECK(!scroll_in_progress_); ++ // DCHECK(!scroll_in_progress_); + scroll_in_progress_ = true; + + WebGestureEvent scroll_begin(gesture_update); +diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc +index 97ca37d843be..fdc4a3f90c64 100644 +--- a/content/browser/renderer_host/render_widget_host_impl.cc ++++ b/content/browser/renderer_host/render_widget_host_impl.cc +@@ -1230,8 +1238,8 @@ void RenderWidgetHostImpl::ForwardGestureEventWithLatencyInfo( + // GSB and GSU events instead of sending them to the renderer and continues + // to progress the fling. So, the renderer doesn't receive two GSB events + // without any GSE in between. +- DCHECK(!is_in_gesture_scroll_[gesture_event.SourceDevice()] || +- FlingCancellationIsDeferred()); ++ // DCHECK(!is_in_gesture_scroll_[gesture_event.SourceDevice()] || ++ // FlingCancellationIsDeferred()); + is_in_gesture_scroll_[gesture_event.SourceDevice()] = true; + } else if (gesture_event.GetType() == + blink::WebInputEvent::kGestureScrollEnd) { diff --git a/patches/common/chromium/disable_user_gesture_requirement_for_beforeunload_dialogs.patch b/patches/common/chromium/disable_user_gesture_requirement_for_beforeunload_dialogs.patch new file mode 100644 index 00000000000..c3b94efedbd --- /dev/null +++ b/patches/common/chromium/disable_user_gesture_requirement_for_beforeunload_dialogs.patch @@ -0,0 +1,15 @@ +diff --git a/third_party/blink/renderer/core/dom/document.cc b/third_party/blink/renderer/core/dom/document.cc +index a39067db8c52..4a0d69dc3fb5 100644 +--- a/third_party/blink/renderer/core/dom/document.cc ++++ b/third_party/blink/renderer/core/dom/document.cc +@@ -3239,7 +3239,9 @@ bool Document::DispatchBeforeUnloadEvent(ChromeClient& chrome_client, + "Blocked attempt to show a 'beforeunload' confirmation panel for a " + "frame that never had a user gesture since its load. " + "https://www.chromestatus.com/feature/5082396709879808")); +- return true; ++ // TODO(alexeykuzmin): Uncomment `return true` when Electron tests are fixed. ++ // See https://github.com/electron/electron/issues/10754 ++ // return true; + } + + if (did_allow_navigation) { diff --git a/patches/common/chromium/dom_storage_map.patch b/patches/common/chromium/dom_storage_map.patch new file mode 100644 index 00000000000..29b0772cfc9 --- /dev/null +++ b/patches/common/chromium/dom_storage_map.patch @@ -0,0 +1,17 @@ +diff --git a/content/common/dom_storage/dom_storage_map.cc b/content/common/dom_storage/dom_storage_map.cc +index 0a6b0176a982..35a1c3c11a58 100644 +--- a/content/common/dom_storage/dom_storage_map.cc ++++ b/content/common/dom_storage/dom_storage_map.cc +@@ -182,10 +182,12 @@ bool DOMStorageMap::SetItemInternal(MapType* map_type, + size_t new_item_size = size_in_storage(key, value); + size_t new_storage_used = storage_used_ - old_item_size + new_item_size; + ++#if 0 // Disable localStorage size limit for Electron. + // Only check quota if the size is increasing, this allows + // shrinking changes to pre-existing files that are over budget. + if (new_item_size > old_item_size && new_storage_used > quota_) + return false; ++#endif + + (*map_type)[key] = value; + ResetKeyIterator(); diff --git a/patches/common/chromium/enable_osr_components.patch b/patches/common/chromium/enable_osr_components.patch new file mode 100644 index 00000000000..fb7f5f9b09b --- /dev/null +++ b/patches/common/chromium/enable_osr_components.patch @@ -0,0 +1,21 @@ +diff --git a/content/browser/renderer_host/input/mouse_wheel_phase_handler.h b/content/browser/renderer_host/input/mouse_wheel_phase_handler.h +index 4f7c03d62930..25b74d9b5236 100644 +--- a/content/browser/renderer_host/input/mouse_wheel_phase_handler.h ++++ b/content/browser/renderer_host/input/mouse_wheel_phase_handler.h +@@ -7,6 +7,7 @@ + + #include "base/timer/timer.h" + #include "content/browser/renderer_host/render_widget_host_delegate.h" ++#include "content/common/content_export.h" + #include "content/public/common/input_event_ack_state.h" + #include "third_party/blink/public/platform/web_mouse_wheel_event.h" + +@@ -55,7 +56,7 @@ enum class FirstScrollUpdateAckState { + // The MouseWheelPhaseHandler is responsible for adding the proper phase to + // wheel events. Phase information is necessary for wheel scrolling since it + // shows the start and end of a scrolling sequence. +-class MouseWheelPhaseHandler { ++class CONTENT_EXPORT MouseWheelPhaseHandler { + public: + MouseWheelPhaseHandler(RenderWidgetHostViewBase* const host_view); + ~MouseWheelPhaseHandler() {} diff --git a/patches/common/chromium/enable_widevine.patch b/patches/common/chromium/enable_widevine.patch new file mode 100644 index 00000000000..99d6badf419 --- /dev/null +++ b/patches/common/chromium/enable_widevine.patch @@ -0,0 +1,13 @@ +diff --git a/third_party/widevine/cdm/widevine.gni b/third_party/widevine/cdm/widevine.gni +index 82a93622585a..cbd10bed9f3b 100644 +--- a/third_party/widevine/cdm/widevine.gni ++++ b/third_party/widevine/cdm/widevine.gni +@@ -7,7 +7,7 @@ import("//media/media_options.gni") + + declare_args() { + # Allow Widevine key system support in Chromium. +- enable_widevine = false ++ enable_widevine = is_mac || is_win + } + + enable_widevine_cdm_host_verification = diff --git a/patches/common/chromium/exclude_next_version_mini_installer_from_deps.patch b/patches/common/chromium/exclude_next_version_mini_installer_from_deps.patch new file mode 100644 index 00000000000..b4eebe11b89 --- /dev/null +++ b/patches/common/chromium/exclude_next_version_mini_installer_from_deps.patch @@ -0,0 +1,13 @@ +diff --git a/chrome/installer/mini_installer/BUILD.gn b/chrome/installer/mini_installer/BUILD.gn +index c44f8a110599..2d48cf1ade70 100644 +--- a/chrome/installer/mini_installer/BUILD.gn ++++ b/chrome/installer/mini_installer/BUILD.gn +@@ -331,7 +331,7 @@ if (is_win) { + testonly = true + data_deps = [ + ":mini_installer", +- ":next_version_mini_installer", ++ # ":next_version_mini_installer", + ] + } + } diff --git a/patches/common/chromium/export_blink_webdisplayitemlist.patch b/patches/common/chromium/export_blink_webdisplayitemlist.patch new file mode 100644 index 00000000000..8f77a4a7b35 --- /dev/null +++ b/patches/common/chromium/export_blink_webdisplayitemlist.patch @@ -0,0 +1,21 @@ +diff --git a/third_party/blink/public/platform/web_display_item_list.h b/third_party/blink/public/platform/web_display_item_list.h +index 31a3f6d8d5f4..0b2a13230fbd 100644 +--- a/third_party/blink/public/platform/web_display_item_list.h ++++ b/third_party/blink/public/platform/web_display_item_list.h +@@ -6,6 +6,7 @@ + #define THIRD_PARTY_BLINK_PUBLIC_PLATFORM_WEB_DISPLAY_ITEM_LIST_H_ + + #include "third_party/blink/public/platform/web_blend_mode.h" ++#include "third_party/blink/public/platform/web_common.h" + #include "third_party/blink/public/platform/web_float_point.h" + #include "third_party/blink/public/platform/web_float_rect.h" + #include "third_party/blink/public/platform/web_rect.h" +@@ -33,7 +34,7 @@ namespace blink { + // 'drawing' items) and operations to be performed when rendering this content + // (stored in 'clip', 'transform', 'filter', etc...). For more details see: + // http://dev.chromium.org/blink/slimming-paint. +-class WebDisplayItemList { ++class BLINK_EXPORT WebDisplayItemList { + public: + virtual ~WebDisplayItemList() = default; + diff --git a/patches/common/chromium/fix-arm64-linking-error.patch b/patches/common/chromium/fix-arm64-linking-error.patch new file mode 100644 index 00000000000..de291eb1252 --- /dev/null +++ b/patches/common/chromium/fix-arm64-linking-error.patch @@ -0,0 +1,13 @@ +diff --git a/skia/BUILD.gn b/skia/BUILD.gn +index c0477a6fe82d..3a020f2e2006 100644 +--- a/skia/BUILD.gn ++++ b/skia/BUILD.gn +@@ -125,7 +125,7 @@ config("skia_library_config") { + + defines = [] + +- if (!is_ios && !use_system_freetype) { ++ if (!is_ios && (is_win || is_mac)) { + defines += [ "SK_FREETYPE_MINIMUM_RUNTIME_VERSION=(((FREETYPE_MAJOR) * 0x01000000) | ((FREETYPE_MINOR) * 0x00010000) | ((FREETYPE_PATCH) * 0x00000100))" ] + } + diff --git a/patches/common/chromium/frame_host_manager.patch b/patches/common/chromium/frame_host_manager.patch new file mode 100644 index 00000000000..e5028708c33 --- /dev/null +++ b/patches/common/chromium/frame_host_manager.patch @@ -0,0 +1,83 @@ +diff --git a/content/browser/frame_host/render_frame_host_manager.cc b/content/browser/frame_host/render_frame_host_manager.cc +index e6f6b3012b02..965b58e237ec 100644 +--- a/content/browser/frame_host/render_frame_host_manager.cc ++++ b/content/browser/frame_host/render_frame_host_manager.cc +@@ -1834,6 +1834,18 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( + bool was_server_redirect = request.navigation_handle() && + request.navigation_handle()->WasServerRedirect(); + ++ BrowserContext* browser_context = ++ delegate_->GetControllerForRenderManager().GetBrowserContext(); ++ // If the navigation can swap SiteInstances, compute the SiteInstance it ++ // should use. ++ // TODO(clamy): We should also consider as a candidate SiteInstance the ++ // speculative SiteInstance that was computed on redirects. ++ scoped_refptr candidate_site_instance = ++ speculative_render_frame_host_ ++ ? speculative_render_frame_host_->GetSiteInstance() ++ : content::SiteInstance::CreateForURL(browser_context, ++ request.common_params().url); ++ + if (frame_tree_node_->IsMainFrame()) { + // Renderer-initiated main frame navigations that may require a + // SiteInstance swap are sent to the browser via the OpenURL IPC and are +@@ -1850,6 +1862,19 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( + + no_renderer_swap_allowed |= + request.from_begin_navigation() && !can_renderer_initiate_transfer; ++ ++ bool has_response_started = ++ (request.state() == NavigationRequest::RESPONSE_STARTED || ++ request.state() == NavigationRequest::FAILED) && ++ !speculative_render_frame_host_; ++ // Gives user a chance to choose a custom site instance. ++ SiteInstance* client_custom_instance = nullptr; ++ GetContentClient()->browser()->OverrideSiteInstanceForNavigation( ++ render_frame_host_.get(), browser_context, request.common_params().url, ++ has_response_started, candidate_site_instance.get(), ++ &client_custom_instance); ++ if (client_custom_instance) ++ return scoped_refptr(client_custom_instance); + } else { + // Subframe navigations will use the current renderer, unless specifically + // allowed to swap processes. +@@ -1861,18 +1886,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( + if (no_renderer_swap_allowed) + return scoped_refptr(current_site_instance); + +- // If the navigation can swap SiteInstances, compute the SiteInstance it +- // should use. +- // TODO(clamy): We should also consider as a candidate SiteInstance the +- // speculative SiteInstance that was computed on redirects. +- SiteInstance* candidate_site_instance = +- speculative_render_frame_host_ +- ? speculative_render_frame_host_->GetSiteInstance() +- : nullptr; +- + scoped_refptr dest_site_instance = GetSiteInstanceForNavigation( + request.common_params().url, request.source_site_instance(), +- request.dest_site_instance(), candidate_site_instance, ++ request.dest_site_instance(), candidate_site_instance.get(), + request.common_params().transition, + request.restore_type() != RestoreType::NONE, request.is_view_source(), + was_server_redirect); +diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h +index 746760e8596c..99d9e0770f32 100644 +--- a/content/public/browser/content_browser_client.h ++++ b/content/public/browser/content_browser_client.h +@@ -181,6 +181,15 @@ class CONTENT_EXPORT ContentBrowserClient { + public: + virtual ~ContentBrowserClient() {} + ++ // Electron: Allows overriding the SiteInstance when navigating. ++ virtual void OverrideSiteInstanceForNavigation( ++ RenderFrameHost* render_frame_host, ++ BrowserContext* browser_context, ++ const GURL& dest_url, ++ bool has_response_started, ++ SiteInstance* candidate_site_instance, ++ SiteInstance** new_instance) {} ++ + // Allows the embedder to set any number of custom BrowserMainParts + // implementations for the browser startup code. See comments in + // browser_main_parts.h. diff --git a/patches/common/chromium/gin_enable_disable_v8_platform.patch b/patches/common/chromium/gin_enable_disable_v8_platform.patch new file mode 100644 index 00000000000..8e8d6628d6c --- /dev/null +++ b/patches/common/chromium/gin_enable_disable_v8_platform.patch @@ -0,0 +1,66 @@ +diff --git a/gin/isolate_holder.cc b/gin/isolate_holder.cc +index 56402d477ca3..8ab11bd18783 100644 +--- a/gin/isolate_holder.cc ++++ b/gin/isolate_holder.cc +@@ -116,9 +116,10 @@ IsolateHolder::~IsolateHolder() { + void IsolateHolder::Initialize(ScriptMode mode, + V8ExtrasMode v8_extras_mode, + v8::ArrayBuffer::Allocator* allocator, +- const intptr_t* reference_table) { ++ const intptr_t* reference_table, ++ bool create_v8_platform) { + CHECK(allocator); +- V8Initializer::Initialize(mode, v8_extras_mode); ++ V8Initializer::Initialize(mode, v8_extras_mode, create_v8_platform); + g_array_buffer_allocator = allocator; + g_reference_table = reference_table; + } +diff --git a/gin/public/isolate_holder.h b/gin/public/isolate_holder.h +index 2509aca609f9..94003c6031cf 100644 +--- a/gin/public/isolate_holder.h ++++ b/gin/public/isolate_holder.h +@@ -84,7 +84,8 @@ class GIN_EXPORT IsolateHolder { + static void Initialize(ScriptMode mode, + V8ExtrasMode v8_extras_mode, + v8::ArrayBuffer::Allocator* allocator, +- const intptr_t* reference_table = nullptr); ++ const intptr_t* reference_table = nullptr, ++ bool create_v8_platform = true); + + v8::Isolate* isolate() { return isolate_; } + +diff --git a/gin/v8_initializer.cc b/gin/v8_initializer.cc +index 02d4b1cd6521..ec6d51d7e5d8 100644 +--- a/gin/v8_initializer.cc ++++ b/gin/v8_initializer.cc +@@ -236,12 +236,14 @@ LoadV8FileResult MapOpenedFile(const OpenedFileMap::mapped_type& file_region, + + // static + void V8Initializer::Initialize(IsolateHolder::ScriptMode mode, +- IsolateHolder::V8ExtrasMode v8_extras_mode) { ++ IsolateHolder::V8ExtrasMode v8_extras_mode, ++ bool create_v8_platform) { + static bool v8_is_initialized = false; + if (v8_is_initialized) + return; + +- v8::V8::InitializePlatform(V8Platform::Get()); ++ if (create_v8_platform) ++ v8::V8::InitializePlatform(V8Platform::Get()); + + if (base::FeatureList::IsEnabled(features::kV8OptimizeJavascript)) { + static const char optimize[] = "--opt"; +diff --git a/gin/v8_initializer.h b/gin/v8_initializer.h +index f0a7c5e0fb68..df4ab4f3e4b9 100644 +--- a/gin/v8_initializer.h ++++ b/gin/v8_initializer.h +@@ -21,7 +21,8 @@ class GIN_EXPORT V8Initializer { + public: + // This should be called by IsolateHolder::Initialize(). + static void Initialize(IsolateHolder::ScriptMode mode, +- IsolateHolder::V8ExtrasMode v8_extras_mode); ++ IsolateHolder::V8ExtrasMode v8_extras_mode, ++ bool create_v8_platform = true); + + // Get address and size information for currently loaded snapshot. + // If no snapshot is loaded, the return values are null for addresses diff --git a/patches/common/chromium/gtk_visibility.patch b/patches/common/chromium/gtk_visibility.patch new file mode 100644 index 00000000000..e4b80bc08e0 --- /dev/null +++ b/patches/common/chromium/gtk_visibility.patch @@ -0,0 +1,13 @@ +diff --git a/build/config/linux/gtk/BUILD.gn b/build/config/linux/gtk/BUILD.gn +index eb75461..2116f93 100644 +--- a/build/config/linux/gtk/BUILD.gn ++++ b/build/config/linux/gtk/BUILD.gn +@@ -17,6 +17,8 @@ assert(is_linux, "This file should only be referenced on Linux") + group("gtk") { + visibility = [ + "//chrome/test:interactive_ui_tests", ++ "//electron:*", ++ "//electron/brightray:*", + "//examples:peerconnection_client", + "//gpu/gles2_conform_support:gles2_conform_test_windowless", + "//remoting/host", diff --git a/patches/common/chromium/ignore_rc_check.patch b/patches/common/chromium/ignore_rc_check.patch new file mode 100644 index 00000000000..bcc3aeca29a --- /dev/null +++ b/patches/common/chromium/ignore_rc_check.patch @@ -0,0 +1,17 @@ +diff --git a/build/toolchain/win/tool_wrapper.py b/build/toolchain/win/tool_wrapper.py +index a76e926a8681..c43839a01211 100644 +--- a/build/toolchain/win/tool_wrapper.py ++++ b/build/toolchain/win/tool_wrapper.py +@@ -258,7 +258,11 @@ class WinTool(object): + if rc_exe_exit_code == 0: + import filecmp + # Strip "/fo" prefix. +- assert filecmp.cmp(rc_res_output[3:], rcpy_res_output[3:]) ++ # ------ ++ # Temporarily ignore compares ++ # Nightly builds use very large version numbers that fail this check ++ # FIXME(zacwalk): Enable the assert. ++ # assert filecmp.cmp(rc_res_output[3:], rcpy_res_output[3:]) + return rc_exe_exit_code + + def ExecActionWrapper(self, arch, rspfile, *dirname): diff --git a/patches/common/chromium/latency_info.patch b/patches/common/chromium/latency_info.patch new file mode 100644 index 00000000000..8816063b026 --- /dev/null +++ b/patches/common/chromium/latency_info.patch @@ -0,0 +1,101 @@ +diff --git a/ui/latency/BUILD.gn b/ui/latency/BUILD.gn +index 2aeebd991ae3..27cacb8748c4 100644 +--- a/ui/latency/BUILD.gn ++++ b/ui/latency/BUILD.gn +@@ -5,7 +5,7 @@ + import("//build/config/jumbo.gni") + import("//testing/test.gni") + +-jumbo_source_set("latency") { ++component("latency") { + sources = [ + "fixed_point.cc", + "fixed_point.h", +@@ -18,6 +18,7 @@ jumbo_source_set("latency") { + "latency_tracker.h", + "stream_analyzer.cc", + "stream_analyzer.h", ++ "ui_latency_export.h", + "windowed_analyzer.cc", + "windowed_analyzer.h", + ] +@@ -22,6 +23,8 @@ jumbo_source_set("latency") { + public_deps = [ + "//services/metrics/public/cpp:metrics_cpp", + ] ++ ++ defines = [ "UI_LATENCY_IMPLEMENTATION" ] + } + + jumbo_source_set("test_support") { +diff --git a/ui/latency/latency_info.h b/ui/latency/latency_info.h +index d9d390861562..7b1aa99e8a9c 100644 +--- a/ui/latency/latency_info.h ++++ b/ui/latency/latency_info.h +@@ -16,6 +16,7 @@ + #include "base/time/time.h" + #include "services/metrics/public/cpp/ukm_source_id.h" + #include "ui/gfx/geometry/point_f.h" ++#include "ui/latency/ui_latency_export.h" + + #if !defined(OS_IOS) + #include "ipc/ipc_param_traits.h" // nogncheck +@@ -114,7 +115,7 @@ enum SourceEventType { + SOURCE_EVENT_TYPE_LAST = OTHER, + }; + +-class LatencyInfo { ++class UI_LATENCY_EXPORT LatencyInfo { + public: + struct LatencyComponent { + // Nondecreasing number that can be used to determine what events happened +diff --git a/ui/latency/latency_tracker.h b/ui/latency/latency_tracker.h +index 24397fc4ba6d..ad943fa7ccf7 100644 +--- a/ui/latency/latency_tracker.h ++++ b/ui/latency/latency_tracker.h +@@ -8,12 +8,13 @@ + #include "base/macros.h" + #include "services/metrics/public/cpp/ukm_source_id.h" + #include "ui/latency/latency_info.h" ++#include "ui/latency/ui_latency_export.h" + + namespace ui { + + // Utility class for tracking the latency of events. Relies on LatencyInfo + // components logged by content::RenderWidgetHostLatencyTracker. +-class LatencyTracker { ++class UI_LATENCY_EXPORT LatencyTracker { + public: + explicit LatencyTracker(bool metric_sampling, + ukm::SourceId ukm_source_id = ukm::kInvalidSourceId); +diff --git a/ui/latency/ui_latency_export.h b/ui/latency/ui_latency_export.h +new file mode 100644 +index 0000000..f24ee91 +--- /dev/null ++++ b/ui/latency/ui_latency_export.h +@@ -0,0 +1,25 @@ ++#ifndef UI_LATENCY_UI_LATENCY_EXPORT_H_ ++#define UI_LATENCY_UI_LATENCY_EXPORT_H_ ++ ++#if defined(COMPONENT_BUILD) ++#if defined(WIN32) ++ ++#if defined(UI_LATENCY_IMPLEMENTATION) ++#define UI_LATENCY_EXPORT __declspec(dllexport) ++#else ++#define UI_LATENCY_EXPORT __declspec(dllimport) ++#endif // defined(UI_LATENCY_IMPLEMENTATION) ++ ++#else // defined(WIN32) ++#if defined(UI_LATENCY_IMPLEMENTATION) ++#define UI_LATENCY_EXPORT __attribute__((visibility("default"))) ++#else ++#define UI_LATENCY_EXPORT ++#endif ++#endif ++ ++#else // defined(COMPONENT_BUILD) ++#define UI_LATENCY_EXPORT ++#endif ++ ++#endif // UI_LATENCY_UI_LATENCY_EXPORT_H_ diff --git a/patches/common/chromium/leveldb_ssize_t.patch b/patches/common/chromium/leveldb_ssize_t.patch new file mode 100644 index 00000000000..0867c6ad404 --- /dev/null +++ b/patches/common/chromium/leveldb_ssize_t.patch @@ -0,0 +1,16 @@ +diff --git a/third_party/leveldatabase/port/port_chromium.h b/third_party/leveldatabase/port/port_chromium.h +index a7c449eba19c..acbce7efd582 100644 +--- a/third_party/leveldatabase/port/port_chromium.h ++++ b/third_party/leveldatabase/port/port_chromium.h +@@ -26,7 +26,11 @@ + #endif + + #if defined(OS_WIN) ++# if !defined(_SSIZE_T_) && !defined(_SSIZE_T_DEFINED) + typedef SSIZE_T ssize_t; ++# define _SSIZE_T_ ++# define _SSIZE_T_DEFINED ++# endif + #endif + + namespace leveldb { diff --git a/patches/common/chromium/libgtkui_export.patch b/patches/common/chromium/libgtkui_export.patch new file mode 100644 index 00000000000..d0aa9ec2c5c --- /dev/null +++ b/patches/common/chromium/libgtkui_export.patch @@ -0,0 +1,125 @@ +diff --git a/chrome/browser/ui/libgtkui/app_indicator_icon.h b/chrome/browser/ui/libgtkui/app_indicator_icon.h +index 7815fbb..f17a5c5 100644 +--- a/chrome/browser/ui/libgtkui/app_indicator_icon.h ++++ b/chrome/browser/ui/libgtkui/app_indicator_icon.h +@@ -12,6 +12,7 @@ + #include "base/memory/weak_ptr.h" + #include "base/nix/xdg_util.h" + #include "chrome/browser/ui/libgtkui/gtk_signal.h" ++#include "chrome/browser/ui/libgtkui/libgtkui_export.h" + #include "ui/views/linux_ui/status_icon_linux.h" + + typedef struct _AppIndicator AppIndicator; +@@ -31,7 +32,7 @@ namespace libgtkui { + class AppIndicatorIconMenu; + + // Status icon implementation which uses libappindicator. +-class AppIndicatorIcon : public views::StatusIconLinux { ++class LIBGTKUI_EXPORT AppIndicatorIcon : public views::StatusIconLinux { + public: + // The id uniquely identifies the new status icon from other chrome status + // icons. +diff --git a/chrome/browser/ui/libgtkui/gtk_status_icon.h b/chrome/browser/ui/libgtkui/gtk_status_icon.h +index e4e0da4..af02871 100644 +--- a/chrome/browser/ui/libgtkui/gtk_status_icon.h ++++ b/chrome/browser/ui/libgtkui/gtk_status_icon.h +@@ -10,6 +10,7 @@ + #include "base/macros.h" + #include "base/strings/string16.h" + #include "chrome/browser/ui/libgtkui/gtk_signal.h" ++#include "chrome/browser/ui/libgtkui/libgtkui_export.h" + #include "ui/base/glib/glib_integers.h" + #include "ui/base/glib/glib_signal.h" + #include "ui/views/linux_ui/status_icon_linux.h" +@@ -29,7 +30,7 @@ class AppIndicatorIconMenu; + + // Status icon implementation which uses the system tray X11 spec (via + // GtkStatusIcon). +-class Gtk2StatusIcon : public views::StatusIconLinux { ++class LIBGTKUI_EXPORT Gtk2StatusIcon : public views::StatusIconLinux { + public: + Gtk2StatusIcon(const gfx::ImageSkia& image, const base::string16& tool_tip); + ~Gtk2StatusIcon() override; +diff --git a/chrome/browser/ui/libgtkui/gtk_util.h b/chrome/browser/ui/libgtkui/gtk_util.h +index 665ec57..4ccb088 100644 +--- a/chrome/browser/ui/libgtkui/gtk_util.h ++++ b/chrome/browser/ui/libgtkui/gtk_util.h +@@ -11,6 +11,7 @@ + #include "ui/base/glib/scoped_gobject.h" + #include "ui/native_theme/native_theme.h" + #include "ui/views/window/frame_buttons.h" ++#include "chrome/browser/ui/libgtkui/libgtkui_export.h" + + namespace aura { + class Window; +@@ -51,10 +52,10 @@ SkColor NormalURLColor(SkColor foreground); + // saturation than to look exactly like the foreground color. + SkColor SelectedURLColor(SkColor foreground, SkColor background); + +-void GtkInitFromCommandLine(const base::CommandLine& command_line); ++LIBGTKUI_EXPORT void GtkInitFromCommandLine(const base::CommandLine& command_line); + + // Returns the name of the ".desktop" file associated with our running process. +-std::string GetDesktopName(base::Environment* env); ++LIBGTKUI_EXPORT std::string GetDesktopName(base::Environment* env); + + guint GetGdkKeyCodeForAccelerator(const ui::Accelerator& accelerator); + +@@ -69,7 +70,7 @@ void TurnButtonBlue(GtkWidget* button); + + // Sets |dialog| as transient for |parent|, which will keep it on top and center + // it above |parent|. Do nothing if |parent| is nullptr. +-void SetGtkTransientForAura(GtkWidget* dialog, aura::Window* parent); ++LIBGTKUI_EXPORT void SetGtkTransientForAura(GtkWidget* dialog, aura::Window* parent); + + // Gets the transient parent aura window for |dialog|. + aura::Window* GetAuraTransientParent(GtkWidget* dialog); +diff --git a/chrome/browser/ui/libgtkui/skia_utils_gtk.h b/chrome/browser/ui/libgtkui/skia_utils_gtk.h +index e05fbe9..3afca9a 100644 +--- a/chrome/browser/ui/libgtkui/skia_utils_gtk.h ++++ b/chrome/browser/ui/libgtkui/skia_utils_gtk.h +@@ -7,6 +7,7 @@ + + #include + ++#include "chrome/browser/ui/libgtkui/libgtkui_export.h" + #include "third_party/skia/include/core/SkColor.h" + + typedef struct _GdkColor GdkColor; +@@ -41,7 +42,7 @@ const SkBitmap GdkPixbufToImageSkia(GdkPixbuf* pixbuf); + // Convert and copy a SkBitmap to a GdkPixbuf. NOTE: this uses BGRAToRGBA, so + // it is an expensive operation. The returned GdkPixbuf will have a refcount of + // 1, and the caller is responsible for unrefing it when done. +-GdkPixbuf* GdkPixbufFromSkBitmap(const SkBitmap& bitmap); ++LIBGTKUI_EXPORT GdkPixbuf* GdkPixbufFromSkBitmap(const SkBitmap& bitmap); + + } // namespace libgtkui + +diff --git a/chrome/browser/ui/libgtkui/unity_service.h b/chrome/browser/ui/libgtkui/unity_service.h +index 8d67e14..95fbb27 100644 +--- a/chrome/browser/ui/libgtkui/unity_service.h ++++ b/chrome/browser/ui/libgtkui/unity_service.h +@@ -5,18 +5,20 @@ + #ifndef CHROME_BROWSER_UI_LIBGTKUI_UNITY_SERVICE_H_ + #define CHROME_BROWSER_UI_LIBGTKUI_UNITY_SERVICE_H_ + ++#include "chrome/browser/ui/libgtkui/libgtkui_export.h" ++ + namespace unity { + + // Returns whether unity is currently running. +-bool IsRunning(); ++LIBGTKUI_EXPORT bool IsRunning(); + + // If unity is running, sets the download counter in the dock icon. Any value + // other than 0 displays the badge. +-void SetDownloadCount(int count); ++LIBGTKUI_EXPORT void SetDownloadCount(int count); + + // If unity is running, sets the download progress bar in the dock icon. Any + // value between 0.0 and 1.0 (exclusive) shows the progress bar. +-void SetProgressFraction(float percentage); ++LIBGTKUI_EXPORT void SetProgressFraction(float percentage); + + } // namespace unity + diff --git a/patches/common/chromium/mas-audiodeviceduck.patch b/patches/common/chromium/mas-audiodeviceduck.patch new file mode 100644 index 00000000000..0d4d01c98fd --- /dev/null +++ b/patches/common/chromium/mas-audiodeviceduck.patch @@ -0,0 +1,47 @@ +From d322e351554a4fa1fbaf529769416041031f07e9 Mon Sep 17 00:00:00 2001 +From: Jeremy Apthorp +Date: Mon, 6 Aug 2018 13:02:53 -0700 +Subject: fix: [mas] don't call private api AudioDeviceDuck + +--- + media/audio/mac/audio_low_latency_input_mac.cc | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/media/audio/mac/audio_low_latency_input_mac.cc b/media/audio/mac/audio_low_latency_input_mac.cc +index 173167b54dfb..1c0fda354d03 100644 +--- a/media/audio/mac/audio_low_latency_input_mac.cc ++++ b/media/audio/mac/audio_low_latency_input_mac.cc +@@ -28,12 +28,14 @@ + + namespace { + extern "C" { ++#ifndef MAS_BUILD + // See: + // https://trac.webkit.org/browser/webkit/trunk/Source/WebCore/PAL/pal/spi/cf/CoreAudioSPI.h?rev=228264 + OSStatus AudioDeviceDuck(AudioDeviceID inDevice, + Float32 inDuckedLevel, + const AudioTimeStamp* __nullable inStartTime, + Float32 inRampDuration) __attribute__((weak_import)); ++#endif + } + + } // namespace +@@ -604,6 +606,7 @@ bool AUAudioInputStream::OpenVoiceProcessingAU() { + return false; + } + ++#ifndef MAS_BUILD + if (AudioDeviceDuck != nullptr) { + // Undo the ducking. + // Obtain the AudioDeviceID of the default output AudioDevice. +@@ -619,6 +622,7 @@ bool AUAudioInputStream::OpenVoiceProcessingAU() { + AudioDeviceDuck(output_device, 1.0, nullptr, 0.5); + } + } ++#endif + + return true; + } +-- +2.17.0 + diff --git a/patches/common/chromium/mas-cfisobjc.patch b/patches/common/chromium/mas-cfisobjc.patch new file mode 100644 index 00000000000..efac7300642 --- /dev/null +++ b/patches/common/chromium/mas-cfisobjc.patch @@ -0,0 +1,44 @@ +From 9fb1ac04b1a3e7ec53e27cf1f413469d04360d1e Mon Sep 17 00:00:00 2001 +From: Jeremy Apthorp +Date: Mon, 6 Aug 2018 17:11:14 -0700 +Subject: fix: [mas] remove usage of _CFIsObjC + +--- + base/mac/foundation_util.mm | 7 +------ + 1 file changed, 1 insertion(+), 6 deletions(-) + +diff --git a/base/mac/foundation_util.mm b/base/mac/foundation_util.mm +index aec8c0f6398c..6a6dfc272d45 100644 +--- a/base/mac/foundation_util.mm ++++ b/base/mac/foundation_util.mm +@@ -25,7 +25,6 @@ + extern "C" { + CFTypeID SecACLGetTypeID(); + CFTypeID SecTrustedApplicationGetTypeID(); +-Boolean _CFIsObjC(CFTypeID typeID, CFTypeRef obj); + } // extern "C" + #endif + +@@ -323,8 +322,7 @@ NSFont* CFToNSCast(CTFontRef cf_val) { + const_cast(reinterpret_cast(cf_val)); + DCHECK(!cf_val || + CTFontGetTypeID() == CFGetTypeID(cf_val) || +- (_CFIsObjC(CTFontGetTypeID(), cf_val) && +- [ns_val isKindOfClass:[NSFont class]])); ++ ([ns_val isKindOfClass:[NSFont class]])); + return ns_val; + } + +@@ -392,9 +390,6 @@ CFCast(const CFTypeRef& cf_val) { + return (CTFontRef)(cf_val); + } + +- if (!_CFIsObjC(CTFontGetTypeID(), cf_val)) +- return NULL; +- + id ns_val = reinterpret_cast(const_cast(cf_val)); + if ([ns_val isKindOfClass:[NSFont class]]) { + return (CTFontRef)(cf_val); +-- +2.17.0 + diff --git a/patches/common/chromium/mas-cgdisplayusesforcetogray.patch b/patches/common/chromium/mas-cgdisplayusesforcetogray.patch new file mode 100644 index 00000000000..fe68a4c578e --- /dev/null +++ b/patches/common/chromium/mas-cgdisplayusesforcetogray.patch @@ -0,0 +1,34 @@ +From 82d0ef64e22c69c0435608276149977d2811a3f7 Mon Sep 17 00:00:00 2001 +From: Jeremy Apthorp +Date: Mon, 6 Aug 2018 10:58:46 -0700 +Subject: fix: [mas] remove usage of CGDisplayUsesForceToGray + +--- + ui/display/mac/screen_mac.mm | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +diff --git a/ui/display/mac/screen_mac.mm b/ui/display/mac/screen_mac.mm +index 4850c795480e..ec34b25a6fe8 100644 +--- a/ui/display/mac/screen_mac.mm ++++ b/ui/display/mac/screen_mac.mm +@@ -106,7 +106,17 @@ Display BuildDisplayForScreen(NSScreen* screen) { + + display.set_color_depth(NSBitsPerPixelFromDepth([screen depth])); + display.set_depth_per_component(NSBitsPerSampleFromDepth([screen depth])); ++#ifdef MAS_BUILD ++ // This is equivalent to the CGDisplayUsesForceToGray() API as at 2018-08-06, ++ // but avoids usage of the private API. ++ CFStringRef app = CFSTR("com.apple.CoreGraphics"); ++ CFStringRef key = CFSTR("DisplayUseForcedGray"); ++ Boolean key_valid = false; ++ display.set_is_monochrome( ++ CFPreferencesGetAppBooleanValue(key, app, &key_valid)); ++#else + display.set_is_monochrome(CGDisplayUsesForceToGray()); ++#endif + + // CGDisplayRotation returns a double. Display::SetRotationAsDegree will + // handle the unexpected situations were the angle is not a multiple of 90. +-- +2.17.0 + diff --git a/patches/common/chromium/mas-lssetapplicationlaunchservicesserverconnectionstatus.patch b/patches/common/chromium/mas-lssetapplicationlaunchservicesserverconnectionstatus.patch new file mode 100644 index 00000000000..f6cec3294ca --- /dev/null +++ b/patches/common/chromium/mas-lssetapplicationlaunchservicesserverconnectionstatus.patch @@ -0,0 +1,27 @@ +From 3fcbe57ff316894349907bf1c85f71d7487f0932 Mon Sep 17 00:00:00 2001 +From: Jeremy Apthorp +Date: Mon, 6 Aug 2018 13:40:24 -0700 +Subject: fix: [mas] don't call LaunchServices private api + +--- + content/gpu/gpu_main.cc | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/content/gpu/gpu_main.cc b/content/gpu/gpu_main.cc +index 115f871094bc..aa47a1c1a51e 100644 +--- a/content/gpu/gpu_main.cc ++++ b/content/gpu/gpu_main.cc +@@ -276,8 +276,10 @@ int GpuMain(const MainFunctionParams& parameters) { + std::unique_ptr pump(new base::MessagePumpNSRunLoop()); + main_message_loop.reset(new base::MessageLoop(std::move(pump))); + ++#ifndef MAS_BUILD + // Tell LaunchServices to continue without a connection to the daemon. + _LSSetApplicationLaunchServicesServerConnectionStatus(0, nullptr); ++#endif + #else + main_message_loop.reset( + new base::MessageLoop(base::MessageLoop::TYPE_DEFAULT)); +-- +2.17.0 + diff --git a/patches/common/chromium/mas_blink_no_private_api.patch b/patches/common/chromium/mas_blink_no_private_api.patch new file mode 100644 index 00000000000..04ba5738576 --- /dev/null +++ b/patches/common/chromium/mas_blink_no_private_api.patch @@ -0,0 +1,112 @@ +diff --git a/third_party/blink/renderer/core/paint/theme_painter_mac.mm b/third_party/blink/renderer/core/paint/theme_painter_mac.mm +index 65e6437c22a6..3b726d196427 100644 +--- a/third_party/blink/renderer/core/paint/theme_painter_mac.mm ++++ b/third_party/blink/renderer/core/paint/theme_painter_mac.mm +@@ -43,6 +43,7 @@ + + // The methods in this file are specific to the Mac OS X platform. + ++#ifndef MAS_BUILD + // Forward declare Mac SPIs. + extern "C" { + void _NSDrawCarbonThemeBezel(NSRect frame, BOOL enabled, BOOL flipped); +@@ -52,6 +53,7 @@ void _NSDrawCarbonThemeListBox(NSRect frame, + BOOL flipped, + BOOL always_yes); + } ++#endif + + namespace blink { + +@@ -74,10 +76,12 @@ bool ThemePainterMac::PaintTextField(const Node* node, + // behavior change while remaining a fragile solution. + // https://bugs.chromium.org/p/chromium/issues/detail?id=658085#c3 + if (!use_ns_text_field_cell) { ++#ifndef MAS_BUILD + _NSDrawCarbonThemeBezel( + CGRect(r), + LayoutTheme::IsEnabled(node) && !LayoutTheme::IsReadOnlyControl(node), + YES); ++#endif + return false; + } + +@@ -163,10 +167,12 @@ bool ThemePainterMac::PaintTextArea(const Node* node, + const PaintInfo& paint_info, + const IntRect& r) { + LocalCurrentGraphicsContext local_context(paint_info.context, r); ++#ifndef MAS_BUILD + _NSDrawCarbonThemeListBox( + CGRect(r), + LayoutTheme::IsEnabled(node) && !LayoutTheme::IsReadOnlyControl(node), + YES, YES); ++#endif + return false; + } + +diff --git a/third_party/blink/renderer/platform/mac/kill_ring_mac.mm b/third_party/blink/renderer/platform/mac/kill_ring_mac.mm +index acf60f09fdb9..6376120a954f 100644 +--- a/third_party/blink/renderer/platform/mac/kill_ring_mac.mm ++++ b/third_party/blink/renderer/platform/mac/kill_ring_mac.mm +@@ -27,6 +27,7 @@ + + namespace blink { + ++#ifndef MAS_BUILD + extern "C" { + + // Kill ring calls. Would be better to use NSKillRing.h, but that's not +@@ -39,38 +40,53 @@ NSString* _NSYankFromKillRing(); + void _NSNewKillRingSequence(); + void _NSSetKillRingToYankedState(); + } ++#endif + + static void InitializeKillRingIfNeeded() { + static bool initialized_kill_ring = false; + if (!initialized_kill_ring) { + initialized_kill_ring = true; ++#ifndef MAS_BUILD + _NSInitializeKillRing(); ++#endif + } + } + + void KillRing::Append(const String& string) { + InitializeKillRingIfNeeded(); ++#ifndef MAS_BUILD + _NSAppendToKillRing(string); ++#endif + } + + void KillRing::Prepend(const String& string) { + InitializeKillRingIfNeeded(); ++#ifndef MAS_BUILD + _NSPrependToKillRing(string); ++#endif + } + + String KillRing::Yank() { + InitializeKillRingIfNeeded(); ++#ifndef MAS_BUILD + return _NSYankFromKillRing(); ++#else ++ return ""; ++#endif + } + + void KillRing::StartNewSequence() { + InitializeKillRingIfNeeded(); ++#ifndef MAS_BUILD + _NSNewKillRingSequence(); ++#endif + } + + void KillRing::SetToYankedState() { + InitializeKillRingIfNeeded(); ++#ifndef MAS_BUILD + _NSSetKillRingToYankedState(); ++#endif + } + + } // namespace blink diff --git a/patches/common/chromium/mas_no_private_api.patch b/patches/common/chromium/mas_no_private_api.patch new file mode 100644 index 00000000000..be607785077 --- /dev/null +++ b/patches/common/chromium/mas_no_private_api.patch @@ -0,0 +1,436 @@ +diff --git a/content/browser/accessibility/browser_accessibility_cocoa.h b/content/browser/accessibility/browser_accessibility_cocoa.h +index a03585269db6..e7b028760bba 100644 +--- a/content/browser/accessibility/browser_accessibility_cocoa.h ++++ b/content/browser/accessibility/browser_accessibility_cocoa.h +@@ -111,7 +111,9 @@ struct AXTextEdit { + @property(nonatomic, readonly) NSNumber* enabled; + // Returns a text marker that points to the last character in the document that + // can be selected with Voiceover. ++#ifndef MAS_BUILD + @property(nonatomic, readonly) id endTextMarker; ++#endif + @property(nonatomic, readonly) NSNumber* expanded; + @property(nonatomic, readonly) NSNumber* focused; + @property(nonatomic, readonly) NSNumber* grabbed; +@@ -147,12 +149,16 @@ struct AXTextEdit { + @property(nonatomic, readonly) NSArray* selectedChildren; + @property(nonatomic, readonly) NSString* selectedText; + @property(nonatomic, readonly) NSValue* selectedTextRange; ++#ifndef MAS_BUILD + @property(nonatomic, readonly) id selectedTextMarkerRange; ++#endif + @property(nonatomic, readonly) NSValue* size; + @property(nonatomic, readonly) NSString* sortDirection; + // Returns a text marker that points to the first character in the document that + // can be selected with Voiceover. ++#ifndef MAS_BUILD + @property(nonatomic, readonly) id startTextMarker; ++#endif + // A string indicating the subrole of this object as far as accessibility + // is concerned. + @property(nonatomic, readonly) NSString* subrole; +diff --git a/content/browser/accessibility/browser_accessibility_cocoa.mm b/content/browser/accessibility/browser_accessibility_cocoa.mm +index 4cff922f28a3..e9c57f7a0879 100644 +--- a/content/browser/accessibility/browser_accessibility_cocoa.mm ++++ b/content/browser/accessibility/browser_accessibility_cocoa.mm +@@ -119,6 +119,7 @@ NSDictionary* attributeToMethodNameMap = nil; + // VoiceOver uses -1 to mean "no limit" for AXResultsLimit. + const int kAXResultsLimitNoLimit = -1; + ++#ifndef MAS_BUILD + extern "C" { + + // The following are private accessibility APIs required for cursor navigation +@@ -325,6 +326,7 @@ NSAttributedString* GetAttributedTextForTextMarkerRange( + AddMisspelledTextAttributes(text_only_objects, attributed_text); + return [attributed_text attributedSubstringFromRange:range]; + } ++#endif + + // Returns an autoreleased copy of the AXNodeData's attribute. + NSString* NSStringForStringAttribute( +@@ -578,7 +580,9 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + {NSAccessibilityDOMIdentifierAttribute, @"domIdentifier"}, + {NSAccessibilityEditableAncestorAttribute, @"editableAncestor"}, + {NSAccessibilityEnabledAttribute, @"enabled"}, ++#ifndef MAS_BUILD + {NSAccessibilityEndTextMarkerAttribute, @"endTextMarker"}, ++#endif + {NSAccessibilityExpandedAttribute, @"expanded"}, + {NSAccessibilityFocusedAttribute, @"focused"}, + {NSAccessibilityGrabbedAttribute, @"grabbed"}, +@@ -609,13 +613,17 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + {NSAccessibilityRowsAttribute, @"rows"}, + // TODO(aboxhall): expose + // NSAccessibilityServesAsTitleForUIElementsAttribute ++#ifndef MAS_BUILD + {NSAccessibilityStartTextMarkerAttribute, @"startTextMarker"}, ++#endif + {NSAccessibilitySelectedAttribute, @"selected"}, + {NSAccessibilitySelectedChildrenAttribute, @"selectedChildren"}, + {NSAccessibilitySelectedTextAttribute, @"selectedText"}, + {NSAccessibilitySelectedTextRangeAttribute, @"selectedTextRange"}, ++#ifndef MAS_BUILD + {NSAccessibilitySelectedTextMarkerRangeAttribute, + @"selectedTextMarkerRange"}, ++#endif + {NSAccessibilitySizeAttribute, @"size"}, + {NSAccessibilitySortDirectionAttribute, @"sortDirection"}, + {NSAccessibilitySubroleAttribute, @"subrole"}, +@@ -1069,6 +1077,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + ax::mojom::Restriction::kDisabled]; + } + ++#ifndef MAS_BUILD + // Returns a text marker that points to the last character in the document that + // can be selected with VoiceOver. + - (id)endTextMarker { +@@ -1080,6 +1089,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + BrowserAccessibilityPositionInstance position = root->CreatePositionAt(0); + return CreateTextMarker(position->CreatePositionAtEndOfAnchor()); + } ++#endif + + - (NSNumber*)expanded { + if (![self instanceActive]) +@@ -1892,6 +1902,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + return [NSValue valueWithRange:NSMakeRange(selStart, selLength)]; + } + ++#ifndef MAS_BUILD + - (id)selectedTextMarkerRange { + if (![self instanceActive]) + return nil; +@@ -1924,6 +1935,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + anchorAffinity, *focusObject, + focusOffset, focusAffinity)); + } ++#endif + + - (NSValue*)size { + if (![self instanceActive]) +@@ -1956,6 +1968,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + return nil; + } + ++#ifndef MAS_BUILD + // Returns a text marker that points to the first character in the document that + // can be selected with VoiceOver. + - (id)startTextMarker { +@@ -1967,6 +1980,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + BrowserAccessibilityPositionInstance position = root->CreatePositionAt(0); + return CreateTextMarker(position->CreatePositionAtStartOfAnchor()); + } ++#endif + + // Returns a subrole based upon the role. + - (NSString*) subrole { +@@ -2247,12 +2261,14 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + NSMutableAttributedString* attributedValue = + [[[NSMutableAttributedString alloc] initWithString:value] autorelease]; + ++#ifndef MAS_BUILD + if (!browserAccessibility_->IsTextOnlyObject()) { + std::vector textOnlyObjects = + BrowserAccessibilityManager::FindTextOnlyObjectsInRange( + *browserAccessibility_, *browserAccessibility_); + AddMisspelledTextAttributes(textOnlyObjects, attributedValue); + } ++#endif + + return [attributedValue attributedSubstringFromRange:range]; + } +@@ -2372,6 +2388,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + return nil; + } + ++#ifndef MAS_BUILD + if ([attribute isEqualToString:@"AXUIElementForTextMarker"]) { + BrowserAccessibilityPositionInstance position = + CreatePositionFromTextMarker(parameter); +@@ -2549,6 +2566,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + NSString* text = GetTextForTextMarkerRange(parameter); + return [NSNumber numberWithInt:[text length]]; + } ++#endif + + if ([attribute isEqualToString: + NSAccessibilityBoundsForRangeParameterizedAttribute]) { +@@ -2586,6 +2604,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + return nil; + } + ++#ifndef MAS_BUILD + if ([attribute isEqualToString: + NSAccessibilityLineTextMarkerRangeForTextMarkerParameterizedAttribute]) { + BrowserAccessibilityPositionInstance position = +@@ -2665,6 +2684,7 @@ NSString* const NSAccessibilityRequiredAttributeChrome = @"AXRequired"; + + return @(child->GetIndexInParent()); + } ++#endif + + return nil; + } +diff --git a/content/browser/accessibility/browser_accessibility_manager_mac.mm b/content/browser/accessibility/browser_accessibility_manager_mac.mm +index 134f855de654..d588ed98839d 100644 +--- a/content/browser/accessibility/browser_accessibility_manager_mac.mm ++++ b/content/browser/accessibility/browser_accessibility_manager_mac.mm +@@ -441,6 +441,7 @@ NSDictionary* BrowserAccessibilityManagerMac:: + [user_info setObject:native_focus_object + forKey:NSAccessibilityTextChangeElement]; + ++#ifndef MAS_BUILD + id selected_text = [native_focus_object selectedTextMarkerRange]; + if (selected_text) { + NSString* const NSAccessibilitySelectedTextMarkerRangeAttribute = +@@ -448,6 +449,7 @@ NSDictionary* BrowserAccessibilityManagerMac:: + [user_info setObject:selected_text + forKey:NSAccessibilitySelectedTextMarkerRangeAttribute]; + } ++#endif + } + } + +diff --git a/content/renderer/renderer_main_platform_delegate_mac.mm b/content/renderer/renderer_main_platform_delegate_mac.mm +index 6b955bdb3724..1775f3b3c1d4 100644 +--- a/content/renderer/renderer_main_platform_delegate_mac.mm ++++ b/content/renderer/renderer_main_platform_delegate_mac.mm +@@ -22,6 +22,7 @@ + #include "sandbox/mac/seatbelt.h" + #include "services/service_manager/sandbox/mac/sandbox_mac.h" + ++#ifndef MAS_BUILD + extern "C" { + void CGSSetDenyWindowServerConnections(bool); + void CGSShutdownServerConnections(); +@@ -30,6 +31,7 @@ void _LSSetApplicationLaunchServicesServerConnectionStatus( + uint64_t flags, + bool (^connection_allowed)(CFDictionaryRef)); + }; ++#endif + + namespace content { + +@@ -38,6 +40,7 @@ namespace { + // This disconnects from the window server, and then indicates that Chrome + // should continue execution without access to launchservicesd. + void DisconnectWindowServer() { ++#ifndef MAS_BUILD + // Now disconnect from WindowServer, after all objects have been warmed up. + // Shutting down the connection requires connecting to WindowServer, + // so do this before actually engaging the sandbox. This may cause two log +@@ -51,6 +54,7 @@ void DisconnectWindowServer() { + SetApplicationIsDaemon(true); + // Tell LaunchServices to continue without a connection to the daemon. + _LSSetApplicationLaunchServicesServerConnectionStatus(0, nullptr); ++#endif + } + + // You are about to read a pretty disgusting hack. In a static initializer, +diff --git a/device/bluetooth/bluetooth_adapter_mac.mm b/device/bluetooth/bluetooth_adapter_mac.mm +index 09123af7c2f0..69d6b926576f 100644 +--- a/device/bluetooth/bluetooth_adapter_mac.mm ++++ b/device/bluetooth/bluetooth_adapter_mac.mm +@@ -32,6 +32,7 @@ + #include "device/bluetooth/bluetooth_low_energy_central_manager_delegate.h" + #include "device/bluetooth/bluetooth_socket_mac.h" + ++#ifndef MAS_BUILD + extern "C" { + // Undocumented IOBluetooth Preference API [1]. Used by `blueutil` [2] and + // `Karabiner` [3] to programmatically control the Bluetooth state. Calling the +@@ -45,6 +46,7 @@ extern "C" { + // [4] https://support.apple.com/kb/PH25091 + void IOBluetoothPreferenceSetControllerPowerState(int state); + } ++#endif + + namespace { + +@@ -118,8 +120,10 @@ BluetoothAdapterMac::BluetoothAdapterMac() + controller_state_function_( + base::BindRepeating(&BluetoothAdapterMac::GetHostControllerState, + base::Unretained(this))), ++#ifndef MAS_BUILD + power_state_function_( + base::BindRepeating(IOBluetoothPreferenceSetControllerPowerState)), ++#endif + should_update_name_(true), + classic_discovery_manager_( + BluetoothDiscoveryManagerMac::CreateClassic(this)), +@@ -302,8 +306,12 @@ bool BluetoothAdapterMac::IsLowEnergyAvailable() { + } + + bool BluetoothAdapterMac::SetPoweredImpl(bool powered) { ++#ifndef MAS_BUILD + power_state_function_.Run(base::strict_cast(powered)); + return true; ++#else ++ return false; ++#endif + } + + void BluetoothAdapterMac::RemovePairingDelegateInternal( +diff --git a/media/audio/BUILD.gn b/media/audio/BUILD.gn +index 10d786fded92..10e6c6772351 100644 +--- a/media/audio/BUILD.gn ++++ b/media/audio/BUILD.gn +@@ -189,6 +189,12 @@ source_set("audio") { + "mac/scoped_audio_unit.cc", + "mac/scoped_audio_unit.h", + ] ++ if (is_mas_build) { ++ sources -= [ ++ "mac/coreaudio_dispatch_override.cc", ++ "mac/coreaudio_dispatch_override.h", ++ ] ++ } + libs += [ + "AudioToolbox.framework", + "AudioUnit.framework", +diff --git a/media/audio/mac/audio_manager_mac.cc b/media/audio/mac/audio_manager_mac.cc +index 1a74579e310b..0a15778d6825 100644 +--- a/media/audio/mac/audio_manager_mac.cc ++++ b/media/audio/mac/audio_manager_mac.cc +@@ -993,7 +993,7 @@ AudioParameters AudioManagerMac::GetPreferredOutputStreamParameters( + + void AudioManagerMac::InitializeOnAudioThread() { + DCHECK(GetTaskRunner()->BelongsToCurrentThread()); +- InitializeCoreAudioDispatchOverride(); ++ // InitializeCoreAudioDispatchOverride(); + power_observer_.reset(new AudioPowerObserver()); + } + +diff --git a/net/dns/dns_config_service_posix.cc b/net/dns/dns_config_service_posix.cc +index 706ba6e8e882..3fbe80c91cd9 100644 +--- a/net/dns/dns_config_service_posix.cc ++++ b/net/dns/dns_config_service_posix.cc +@@ -244,6 +244,7 @@ class DnsConfigServicePosix::Watcher { + + bool Watch() { + bool success = true; ++#ifndef MAS_BUILD + if (!config_watcher_.Watch(base::Bind(&Watcher::OnConfigChanged, + base::Unretained(this)))) { + LOG(ERROR) << "DNS config watch failed to start."; +@@ -265,6 +266,7 @@ class DnsConfigServicePosix::Watcher { + DNS_CONFIG_WATCH_MAX); + } + #endif // !defined(OS_ANDROID) && !defined(OS_IOS) ++#endif + return success; + } + +diff --git a/sandbox/mac/sandbox_compiler.cc b/sandbox/mac/sandbox_compiler.cc +index e524aa7b8510..718d3f963da5 100644 +--- a/sandbox/mac/sandbox_compiler.cc ++++ b/sandbox/mac/sandbox_compiler.cc +@@ -28,6 +28,7 @@ bool SandboxCompiler::InsertStringParam(const std::string& key, + } + + bool SandboxCompiler::CompileAndApplyProfile(std::string* error) { ++#ifndef MAS_BUILD + char* error_internal = nullptr; + std::vector params; + +@@ -44,6 +45,7 @@ bool SandboxCompiler::CompileAndApplyProfile(std::string* error) { + sandbox::Seatbelt::FreeError(error_internal); + return false; + } ++#endif + return true; + } + +diff --git a/sandbox/mac/seatbelt.cc b/sandbox/mac/seatbelt.cc +index dfba0bded9e3..876f96999f53 100644 +--- a/sandbox/mac/seatbelt.cc ++++ b/sandbox/mac/seatbelt.cc +@@ -64,7 +64,11 @@ void Seatbelt::FreeError(char* errorbuf) { + + // static + bool Seatbelt::IsSandboxed() { ++#ifndef MAS_BUILD + return ::sandbox_check(getpid(), NULL, 0); ++#else ++ return true; ++#endif + } + + } // namespace sandbox +diff --git a/sandbox/mac/seatbelt_extension.cc b/sandbox/mac/seatbelt_extension.cc +index 9073364142e8..2356add74dfa 100644 +--- a/sandbox/mac/seatbelt_extension.cc ++++ b/sandbox/mac/seatbelt_extension.cc +@@ -8,6 +8,7 @@ + #include "base/memory/ptr_util.h" + #include "sandbox/mac/seatbelt_extension_token.h" + ++#ifndef MAS_BUILD + // libsandbox private API. + extern "C" { + extern const char* APP_SANDBOX_READ; +@@ -18,6 +19,7 @@ char* sandbox_extension_issue_file(const char* type, + const char* path, + uint32_t flags); + } ++#endif + + namespace sandbox { + +@@ -46,7 +48,11 @@ std::unique_ptr SeatbeltExtension::FromToken( + + bool SeatbeltExtension::Consume() { + DCHECK(!token_.empty()); ++#ifndef MAS_BUILD + handle_ = sandbox_extension_consume(token_.c_str()); ++#else ++ handle_ = -1; ++#endif + return handle_ > 0; + } + +@@ -58,7 +64,11 @@ bool SeatbeltExtension::ConsumePermanently() { + } + + bool SeatbeltExtension::Revoke() { ++#ifndef MAS_BUILD + int rv = sandbox_extension_release(handle_); ++#else ++ int rv = -1; ++#endif + handle_ = 0; + token_.clear(); + return rv == 0; +@@ -76,9 +86,11 @@ SeatbeltExtension::SeatbeltExtension(const std::string& token) + char* SeatbeltExtension::IssueToken(SeatbeltExtension::Type type, + const std::string& resource) { + switch (type) { ++#ifndef MAS_BUILD + case FILE_READ: + return sandbox_extension_issue_file(APP_SANDBOX_READ, resource.c_str(), + 0); ++#endif + default: + NOTREACHED(); + return nullptr; +diff --git a/ui/views/cocoa/bridged_native_widget.mm b/ui/views/cocoa/bridged_native_widget.mm +index 3c6e9903d7df..ddc9061c64d1 100644 +--- a/ui/views/cocoa/bridged_native_widget.mm ++++ b/ui/views/cocoa/bridged_native_widget.mm +@@ -43,6 +43,7 @@ + #include "ui/views/widget/widget_delegate.h" + #include "ui/views/window/dialog_delegate.h" + ++#ifndef MAS_BUILD + extern "C" { + + typedef int32_t CGSConnection; +@@ -52,6 +53,7 @@ CGError CGSSetWindowBackgroundBlurRadius(CGSConnection connection, + int radius); + + } ++#endif + + // The NSView that hosts the composited CALayer drawing the UI. It fills the + // window but is not hittable so that accessibility hit tests always go to the diff --git a/patches/common/chromium/net_url_request_job.patch b/patches/common/chromium/net_url_request_job.patch new file mode 100644 index 00000000000..40d195a6fad --- /dev/null +++ b/patches/common/chromium/net_url_request_job.patch @@ -0,0 +1,12 @@ +diff --git a/net/url_request/url_request_job.h b/net/url_request/url_request_job.h +index 2341999..3011bf7 100644 +--- a/net/url_request/url_request_job.h ++++ b/net/url_request/url_request_job.h +@@ -269,6 +269,7 @@ class NET_EXPORT URLRequestJob : public base::PowerObserver { + void OnCallToDelegate(); + void OnCallToDelegateComplete(); + ++ public: + // Called to read raw (pre-filtered) data from this Job. Reads at most + // |buf_size| bytes into |buf|. + // Possible return values: diff --git a/patches/common/chromium/no_cache_storage_check.patch b/patches/common/chromium/no_cache_storage_check.patch new file mode 100644 index 00000000000..d2c71077169 --- /dev/null +++ b/patches/common/chromium/no_cache_storage_check.patch @@ -0,0 +1,13 @@ +diff --git a/content/browser/cache_storage/cache_storage.cc b/content/browser/cache_storage/cache_storage.cc +index ce6a21b..10a3b18 100644 +--- a/content/browser/cache_storage/cache_storage.cc ++++ b/content/browser/cache_storage/cache_storage.cc +@@ -129,7 +129,7 @@ class CacheStorage::CacheLoader { + blob_context_(blob_context), + cache_storage_(cache_storage), + origin_(origin) { +- DCHECK(!origin_.unique()); ++ // DCHECK(!origin_.unique()); + } + + virtual ~CacheLoader() {} diff --git a/patches/common/chromium/no_stack_dumping.patch b/patches/common/chromium/no_stack_dumping.patch new file mode 100644 index 00000000000..b4203dcbd9e --- /dev/null +++ b/patches/common/chromium/no_stack_dumping.patch @@ -0,0 +1,13 @@ +diff --git a/content/app/content_main_runner.cc b/content/app/content_main_runner.cc +index c283922..397ba80 100644 +--- a/content/app/content_main_runner.cc ++++ b/content/app/content_main_runner.cc +@@ -657,7 +657,7 @@ class ContentMainRunnerImpl : public ContentMainRunner { + + InitializeV8IfNeeded(command_line, process_type); + +-#if !defined(OFFICIAL_BUILD) ++#if 0 + #if defined(OS_WIN) + bool should_enable_stack_dump = !process_type.empty(); + #else diff --git a/patches/common/chromium/out_of_process_instance.patch b/patches/common/chromium/out_of_process_instance.patch new file mode 100644 index 00000000000..d173669afec --- /dev/null +++ b/patches/common/chromium/out_of_process_instance.patch @@ -0,0 +1,15 @@ +diff --git a/pdf/out_of_process_instance.cc b/pdf/out_of_process_instance.cc +index 8b9c9f19a3dd..c4d801135053 100644 +--- a/pdf/out_of_process_instance.cc ++++ b/pdf/out_of_process_instance.cc +@@ -333,7 +333,9 @@ bool OutOfProcessInstance::Init(uint32_t argc, + std::string document_url = document_url_var.AsString(); + base::StringPiece document_url_piece(document_url); + is_print_preview_ = IsPrintPreviewUrl(document_url_piece); +- if (!document_url_piece.starts_with(kChromeExtension) && !is_print_preview_) ++ if (!document_url_piece.starts_with(kChromeExtension) && ++ !document_url_piece.starts_with("chrome://pdf-viewer") && ++ !is_print_preview_) + return false; + + // Check if the plugin is full frame. This is passed in from JS. diff --git a/patches/common/chromium/pepper_flash.patch b/patches/common/chromium/pepper_flash.patch new file mode 100644 index 00000000000..61395ba3f34 --- /dev/null +++ b/patches/common/chromium/pepper_flash.patch @@ -0,0 +1,484 @@ +diff --git a/chrome/browser/renderer_host/pepper/chrome_browser_pepper_host_factory.h b/chrome/browser/renderer_host/pepper/chrome_browser_pepper_host_factory.h +index 735da93c3cab..533f53fbc423 100644 +--- a/chrome/browser/renderer_host/pepper/chrome_browser_pepper_host_factory.h ++++ b/chrome/browser/renderer_host/pepper/chrome_browser_pepper_host_factory.h +@@ -5,6 +5,7 @@ + #ifndef CHROME_BROWSER_RENDERER_HOST_PEPPER_CHROME_BROWSER_PEPPER_HOST_FACTORY_H_ + #define CHROME_BROWSER_RENDERER_HOST_PEPPER_CHROME_BROWSER_PEPPER_HOST_FACTORY_H_ + ++#include "base/component_export.h" + #include "base/macros.h" + #include "ppapi/host/host_factory.h" + +@@ -12,7 +13,8 @@ namespace content { + class BrowserPpapiHost; + } // namespace content + +-class ChromeBrowserPepperHostFactory : public ppapi::host::HostFactory { ++class COMPONENT_EXPORT(PEPPER_FLASH) ChromeBrowserPepperHostFactory ++ : public ppapi::host::HostFactory { + public: + // Non-owning pointer to the filter must outlive this class. + explicit ChromeBrowserPepperHostFactory(content::BrowserPpapiHost* host); +diff --git a/chrome/browser/renderer_host/pepper/pepper_broker_message_filter.cc b/chrome/browser/renderer_host/pepper/pepper_broker_message_filter.cc +index f4f1741a8ecf..103238cdd53f 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_broker_message_filter.cc ++++ b/chrome/browser/renderer_host/pepper/pepper_broker_message_filter.cc +@@ -6,10 +6,12 @@ + + #include + ++#if 0 + #include "chrome/browser/content_settings/host_content_settings_map_factory.h" + #include "chrome/browser/profiles/profile.h" + #include "components/content_settings/core/browser/host_content_settings_map.h" + #include "components/content_settings/core/common/content_settings.h" ++#endif + #include "content/public/browser/browser_ppapi_host.h" + #include "content/public/browser/browser_thread.h" + #include "content/public/browser/render_process_host.h" +@@ -57,6 +59,7 @@ int32_t PepperBrokerMessageFilter::OnIsAllowed( + RenderProcessHost::FromID(render_process_id_); + if (!render_process_host) + return PP_ERROR_FAILED; ++#if 0 + Profile* profile = + Profile::FromBrowserContext(render_process_host->GetBrowserContext()); + HostContentSettingsMap* content_settings = +@@ -68,5 +71,6 @@ int32_t PepperBrokerMessageFilter::OnIsAllowed( + std::string()); + if (setting == CONTENT_SETTING_ALLOW) + return PP_OK; +- return PP_ERROR_FAILED; ++#endif ++ return PP_OK; + } +diff --git a/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.cc b/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.cc +index 1c1844a9eb71..2c9834b11d34 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.cc ++++ b/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.cc +@@ -6,9 +6,11 @@ + + #include "base/time/time.h" + #include "build/build_config.h" ++#if 0 + #include "chrome/browser/content_settings/cookie_settings_factory.h" + #include "chrome/browser/profiles/profile.h" + #include "components/content_settings/core/browser/cookie_settings.h" ++#endif + #include "content/public/browser/browser_context.h" + #include "content/public/browser/browser_ppapi_host.h" + #include "content/public/browser/browser_thread.h" +@@ -40,6 +42,7 @@ using content::ServiceManagerConnection; + + namespace { + ++#if 0 + // Get the CookieSettings on the UI thread for the given render process ID. + scoped_refptr GetCookieSettings( + int render_process_id) { +@@ -53,6 +56,7 @@ scoped_refptr GetCookieSettings( + } + return NULL; + } ++#endif + + void PepperBindConnectorRequest( + service_manager::mojom::ConnectorRequest connector_request) { +@@ -70,7 +74,9 @@ PepperFlashBrowserHost::PepperFlashBrowserHost(BrowserPpapiHost* host, + PP_Instance instance, + PP_Resource resource) + : ResourceHost(host->GetPpapiHost(), instance, resource), ++#if 0 + host_(host), ++#endif + delay_timer_(FROM_HERE, base::TimeDelta::FromSeconds(45), this, + &PepperFlashBrowserHost::OnDelayTimerFired), + weak_factory_(this) { +@@ -122,6 +128,7 @@ int32_t PepperFlashBrowserHost::OnGetLocalTimeZoneOffset( + + int32_t PepperFlashBrowserHost::OnGetLocalDataRestrictions( + ppapi::host::HostMessageContext* context) { ++#if 0 + // Getting the Flash LSO settings requires using the CookieSettings which + // belong to the profile which lives on the UI thread. We lazily initialize + // |cookie_settings_| by grabbing the reference from the UI thread and then +@@ -144,9 +151,11 @@ int32_t PepperFlashBrowserHost::OnGetLocalDataRestrictions( + document_url, + plugin_url)); + } +- return PP_OK_COMPLETIONPENDING; ++#endif ++ return PP_FLASHLSORESTRICTIONS_IN_MEMORY; + } + ++#if 0 + void PepperFlashBrowserHost::GetLocalDataRestrictions( + ppapi::host::ReplyMessageContext reply_context, + const GURL& document_url, +@@ -175,6 +184,7 @@ void PepperFlashBrowserHost::GetLocalDataRestrictions( + PpapiPluginMsg_Flash_GetLocalDataRestrictionsReply( + static_cast(restrictions))); + } ++#endif + + device::mojom::WakeLock* PepperFlashBrowserHost::GetWakeLock() { + // Here is a lazy binding, and will not reconnect after connection error. +diff --git a/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.h b/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.h +index ff0b687a51b6..ab6d96cbe9f8 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.h ++++ b/chrome/browser/renderer_host/pepper/pepper_flash_browser_host.h +@@ -23,9 +23,11 @@ namespace content { + class BrowserPpapiHost; + } + ++#if 0 + namespace content_settings { + class CookieSettings; + } ++#endif + + class GURL; + +@@ -51,15 +53,19 @@ class PepperFlashBrowserHost : public ppapi::host::ResourceHost { + const base::Time& t); + int32_t OnGetLocalDataRestrictions(ppapi::host::HostMessageContext* context); + ++#if 0 + void GetLocalDataRestrictions( + ppapi::host::ReplyMessageContext reply_context, + const GURL& document_url, + const GURL& plugin_url, + scoped_refptr cookie_settings); ++#endif + + device::mojom::WakeLock* GetWakeLock(); + ++#if 0 + content::BrowserPpapiHost* host_; ++#endif + int render_process_id_; + + // Requests a wake lock to prevent going to sleep, and a timer to cancel it +@@ -67,8 +73,10 @@ class PepperFlashBrowserHost : public ppapi::host::ResourceHost { + device::mojom::WakeLockPtr wake_lock_; + base::DelayTimer delay_timer_; + ++#if 0 + // For fetching the Flash LSO settings. + scoped_refptr cookie_settings_; ++#endif + base::WeakPtrFactory weak_factory_; + + DISALLOW_COPY_AND_ASSIGN(PepperFlashBrowserHost); +diff --git a/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.cc b/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.cc +index e267746783bd..bc84b44ceb27 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.cc ++++ b/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.cc +@@ -18,6 +18,7 @@ + #include "content/public/browser/child_process_security_policy.h" + #include "content/public/browser/render_frame_host.h" + #include "content/public/common/pepper_plugin_info.h" ++#include "net/base/network_interfaces.h" + #include "ppapi/c/pp_errors.h" + #include "ppapi/host/dispatch_host_message.h" + #include "ppapi/host/host_message_context.h" +@@ -127,7 +128,9 @@ PepperFlashDRMHost::PepperFlashDRMHost(BrowserPpapiHost* host, + content::ChildProcessSecurityPolicy::GetInstance()->GrantReadFile( + render_process_id, voucher_file); + ++#if 0 + fetcher_ = new DeviceIDFetcher(render_process_id); ++#endif + monitor_finder_ = new MonitorFinder(render_process_id, render_frame_id); + monitor_finder_->GetMonitor(); + } +@@ -150,12 +153,18 @@ int32_t PepperFlashDRMHost::OnResourceMessageReceived( + + int32_t PepperFlashDRMHost::OnHostMsgGetDeviceID( + ppapi::host::HostMessageContext* context) { ++#if 0 + if (!fetcher_->Start(base::Bind(&PepperFlashDRMHost::GotDeviceID, + weak_factory_.GetWeakPtr(), + context->MakeReplyMessageContext()))) { + return PP_ERROR_INPROGRESS; + } +- return PP_OK_COMPLETIONPENDING; ++#endif ++ static std::string id; ++ if (id.empty()) ++ id = net::GetHostName(); ++ context->reply_msg = PpapiPluginMsg_FlashDRM_GetDeviceIDReply(id); ++ return PP_OK; + } + + int32_t PepperFlashDRMHost::OnHostMsgGetHmonitor( +@@ -184,6 +193,7 @@ int32_t PepperFlashDRMHost::OnHostMsgMonitorIsExternal( + return PP_OK; + } + ++#if 0 + void PepperFlashDRMHost::GotDeviceID( + ppapi::host::ReplyMessageContext reply_context, + const std::string& id, +@@ -196,3 +206,4 @@ void PepperFlashDRMHost::GotDeviceID( + host()->SendReply(reply_context, + PpapiPluginMsg_FlashDRM_GetDeviceIDReply(id)); + } ++#endif +diff --git a/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.h b/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.h +index faa83c9d32e5..bbae9c21b59a 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.h ++++ b/chrome/browser/renderer_host/pepper/pepper_flash_drm_host.h +@@ -11,7 +11,9 @@ + + #include "base/macros.h" + #include "base/memory/weak_ptr.h" ++#if 0 + #include "chrome/browser/renderer_host/pepper/device_id_fetcher.h" ++#endif + #include "ppapi/host/host_message_context.h" + #include "ppapi/host/resource_host.h" + +@@ -50,7 +52,9 @@ class PepperFlashDRMHost : public ppapi::host::ResourceHost { + const std::string& id, + int32_t result); + ++#if 0 + scoped_refptr fetcher_; ++#endif + scoped_refptr monitor_finder_; + + base::WeakPtrFactory weak_factory_; +diff --git a/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.cc b/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.cc +index 5599a2d3d62f..532c7290cc36 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.cc ++++ b/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.cc +@@ -7,16 +7,20 @@ + #include + + #include "base/macros.h" ++#if 0 + #include "chrome/browser/browser_process.h" + #include "chrome/browser/profiles/profile.h" + #include "chrome/browser/profiles/profile_manager.h" + #include "chrome/common/chrome_switches.h" + #include "chrome/common/pepper_permission_util.h" ++#endif + #include "content/public/browser/browser_ppapi_host.h" + #include "content/public/browser/browser_thread.h" + #include "content/public/browser/child_process_security_policy.h" + #include "content/public/browser/render_view_host.h" ++#if 0 + #include "extensions/buildflags/buildflags.h" ++#endif + #include "ppapi/c/pp_errors.h" + #include "ppapi/host/dispatch_host_message.h" + #include "ppapi/host/host_message_context.h" +@@ -25,12 +29,11 @@ + #include "ppapi/shared_impl/file_system_util.h" + #include "storage/browser/fileapi/isolated_context.h" + +-#if BUILDFLAG(ENABLE_EXTENSIONS) ++#if 0 + #include "extensions/browser/extension_registry.h" + #include "extensions/common/constants.h" + #include "extensions/common/extension.h" + #include "extensions/common/extension_set.h" +-#endif + + namespace { + +@@ -40,6 +43,7 @@ const char* kPredefinedAllowedCrxFsOrigins[] = { + }; + + } // namespace ++#endif + + // static + PepperIsolatedFileSystemMessageFilter* +@@ -67,8 +71,10 @@ PepperIsolatedFileSystemMessageFilter::PepperIsolatedFileSystemMessageFilter( + profile_directory_(profile_directory), + document_url_(document_url), + ppapi_host_(ppapi_host) { ++#if 0 + for (size_t i = 0; i < arraysize(kPredefinedAllowedCrxFsOrigins); ++i) + allowed_crxfs_origins_.insert(kPredefinedAllowedCrxFsOrigins[i]); ++#endif + } + + PepperIsolatedFileSystemMessageFilter:: +@@ -94,6 +100,7 @@ int32_t PepperIsolatedFileSystemMessageFilter::OnResourceMessageReceived( + return PP_ERROR_FAILED; + } + ++#if 0 + Profile* PepperIsolatedFileSystemMessageFilter::GetProfile() { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + ProfileManager* profile_manager = g_browser_process->profile_manager(); +@@ -120,6 +127,7 @@ std::string PepperIsolatedFileSystemMessageFilter::CreateCrxFileSystem( + return std::string(); + #endif + } ++#endif + + int32_t PepperIsolatedFileSystemMessageFilter::OnOpenFileSystem( + ppapi::host::HostMessageContext* context, +@@ -128,7 +136,7 @@ int32_t PepperIsolatedFileSystemMessageFilter::OnOpenFileSystem( + case PP_ISOLATEDFILESYSTEMTYPE_PRIVATE_INVALID: + break; + case PP_ISOLATEDFILESYSTEMTYPE_PRIVATE_CRX: +- return OpenCrxFileSystem(context); ++ return PP_ERROR_NOTSUPPORTED; + case PP_ISOLATEDFILESYSTEMTYPE_PRIVATE_PLUGINPRIVATE: + return OpenPluginPrivateFileSystem(context); + } +@@ -138,6 +146,7 @@ int32_t PepperIsolatedFileSystemMessageFilter::OnOpenFileSystem( + return PP_ERROR_FAILED; + } + ++#if 0 + int32_t PepperIsolatedFileSystemMessageFilter::OpenCrxFileSystem( + ppapi::host::HostMessageContext* context) { + #if BUILDFLAG(ENABLE_EXTENSIONS) +@@ -176,6 +185,7 @@ int32_t PepperIsolatedFileSystemMessageFilter::OpenCrxFileSystem( + return PP_ERROR_NOTSUPPORTED; + #endif + } ++#endif + + int32_t PepperIsolatedFileSystemMessageFilter::OpenPluginPrivateFileSystem( + ppapi::host::HostMessageContext* context) { +diff --git a/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.h b/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.h +index ca7f87b973e6..f73b596ce78e 100644 +--- a/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.h ++++ b/chrome/browser/renderer_host/pepper/pepper_isolated_file_system_message_filter.h +@@ -19,7 +19,9 @@ + #include "ppapi/host/resource_message_filter.h" + #include "url/gurl.h" + ++#if 0 + class Profile; ++#endif + + namespace content { + class BrowserPpapiHost; +@@ -53,16 +55,20 @@ class PepperIsolatedFileSystemMessageFilter + + ~PepperIsolatedFileSystemMessageFilter() override; + ++#if 0 + Profile* GetProfile(); + + // Returns filesystem id of isolated filesystem if valid, or empty string + // otherwise. This must run on the UI thread because ProfileManager only + // allows access on that thread. + std::string CreateCrxFileSystem(Profile* profile); ++#endif + + int32_t OnOpenFileSystem(ppapi::host::HostMessageContext* context, + PP_IsolatedFileSystemType_Private type); ++#if 0 + int32_t OpenCrxFileSystem(ppapi::host::HostMessageContext* context); ++#endif + int32_t OpenPluginPrivateFileSystem(ppapi::host::HostMessageContext* context); + + const int render_process_id_; +@@ -73,8 +79,10 @@ class PepperIsolatedFileSystemMessageFilter + // Not owned by this object. + ppapi::host::PpapiHost* ppapi_host_; + ++#if 0 + // Set of origins that can use CrxFs private APIs from NaCl. + std::set allowed_crxfs_origins_; ++#endif + + DISALLOW_COPY_AND_ASSIGN(PepperIsolatedFileSystemMessageFilter); + }; +diff --git a/chrome/renderer/pepper/chrome_renderer_pepper_host_factory.cc b/chrome/renderer/pepper/chrome_renderer_pepper_host_factory.cc +index d63e90b6c507..c98a7bd07ddd 100644 +--- a/chrome/renderer/pepper/chrome_renderer_pepper_host_factory.cc ++++ b/chrome/renderer/pepper/chrome_renderer_pepper_host_factory.cc +@@ -10,8 +10,10 @@ + #include "chrome/renderer/pepper/pepper_flash_fullscreen_host.h" + #include "chrome/renderer/pepper/pepper_flash_menu_host.h" + #include "chrome/renderer/pepper/pepper_flash_renderer_host.h" ++#if 0 + #include "chrome/renderer/pepper/pepper_uma_host.h" + #include "components/pdf/renderer/pepper_pdf_host.h" ++#endif + #include "content/public/renderer/renderer_ppapi_host.h" + #include "ppapi/host/ppapi_host.h" + #include "ppapi/host/resource_host.h" +@@ -86,6 +88,7 @@ ChromeRendererPepperHostFactory::CreateResourceHost( + } + } + ++#if 0 + if (host_->GetPpapiHost()->permissions().HasPermission( + ppapi::PERMISSION_PDF)) { + switch (message.type()) { +@@ -104,6 +107,7 @@ ChromeRendererPepperHostFactory::CreateResourceHost( + return std::make_unique(host_, instance, resource); + } + } ++#endif + + return nullptr; + } +diff --git a/chrome/renderer/pepper/pepper_flash_renderer_host.cc b/chrome/renderer/pepper/pepper_flash_renderer_host.cc +index 66a532e2cb41..e776d0e96c4a 100644 +--- a/chrome/renderer/pepper/pepper_flash_renderer_host.cc ++++ b/chrome/renderer/pepper/pepper_flash_renderer_host.cc +@@ -13,7 +13,9 @@ + #include "base/macros.h" + #include "base/metrics/histogram_macros.h" + #include "base/strings/string_util.h" ++#if 0 + #include "components/pdf/renderer/pepper_pdf_host.h" ++#endif + #include "content/public/renderer/pepper_plugin_instance.h" + #include "content/public/renderer/render_thread.h" + #include "content/public/renderer/renderer_ppapi_host.h" +@@ -130,9 +132,11 @@ bool IsSimpleHeader(const std::string& lower_case_header_name, + } + + void RecordFlashNavigateUsage(FlashNavigateUsage usage) { ++#if 0 + DCHECK_NE(FLASH_NAVIGATE_USAGE_ENUM_COUNT, usage); + UMA_HISTOGRAM_ENUMERATION( + "Plugin.FlashNavigateUsage", usage, FLASH_NAVIGATE_USAGE_ENUM_COUNT); ++#endif + } + + } // namespace +@@ -374,6 +378,8 @@ int32_t PepperFlashRendererHost::OnIsRectTopmost( + + int32_t PepperFlashRendererHost::OnInvokePrinting( + ppapi::host::HostMessageContext* host_context) { ++#if 0 + pdf::PepperPDFHost::InvokePrintingForInstance(pp_instance()); +- return PP_OK; ++#endif ++ return PP_ERROR_FAILED; + } +diff --git a/chrome/renderer/pepper/pepper_helper.h b/chrome/renderer/pepper/pepper_helper.h +index e021c964da3d..e035f0fb9e2b 100644 +--- a/chrome/renderer/pepper/pepper_helper.h ++++ b/chrome/renderer/pepper/pepper_helper.h +@@ -6,12 +6,14 @@ + #define CHROME_RENDERER_PEPPER_PEPPER_HELPER_H_ + + #include "base/compiler_specific.h" ++#include "base/component_export.h" + #include "base/macros.h" + #include "content/public/renderer/render_frame_observer.h" + + // This class listens for Pepper creation events from the RenderFrame and + // attaches the parts required for Chrome-specific plugin support. +-class PepperHelper : public content::RenderFrameObserver { ++class COMPONENT_EXPORT(PEPPER_FLASH) PepperHelper ++ : public content::RenderFrameObserver { + public: + explicit PepperHelper(content::RenderFrame* render_frame); + ~PepperHelper() override; diff --git a/patches/common/chromium/protobuf_build_gn.patch b/patches/common/chromium/protobuf_build_gn.patch new file mode 100644 index 00000000000..4f134816aa9 --- /dev/null +++ b/patches/common/chromium/protobuf_build_gn.patch @@ -0,0 +1,16 @@ +diff --git a/BUILD.gn b/BUILD.gn +index 067416ed38f4..9fa07961c5b8 100644 +--- a/third_party/protobuf/BUILD.gn ++++ b/third_party/protobuf/BUILD.gn +@@ -599,6 +599,11 @@ if (current_toolchain == host_toolchain) { + + configs -= [ "//build/config/compiler:chromium_code" ] + configs += [ "//build/config/compiler:no_chromium_code" ] ++ if (is_win) { ++ # https://crbug.com/703251 ++ configs -= [ "//build/config/win:default_incremental_linking" ] ++ configs += [ "//build/config/win:no_incremental_linking" ] ++ } + + cflags = protobuf_lite_cflags + diff --git a/patches/common/chromium/render_widget_host_view_base.patch b/patches/common/chromium/render_widget_host_view_base.patch new file mode 100644 index 00000000000..dbf5564508f --- /dev/null +++ b/patches/common/chromium/render_widget_host_view_base.patch @@ -0,0 +1,70 @@ +diff --git a/content/browser/renderer_host/render_widget_host_view_base.cc b/content/browser/renderer_host/render_widget_host_view_base.cc +index 09a37c1a2c70..ff8c2db3fdae 100644 +--- a/content/browser/renderer_host/render_widget_host_view_base.cc ++++ b/content/browser/renderer_host/render_widget_host_view_base.cc +@@ -399,6 +399,15 @@ viz::FrameSinkId RenderWidgetHostViewBase::FrameSinkIdAtPoint( + return frame_sink_id.is_valid() ? frame_sink_id : GetFrameSinkId(); + } + ++RenderWidgetHostViewBase* RenderWidgetHostViewBase::CreateViewForWidget( ++ RenderWidgetHost* render_widget_host, ++ RenderWidgetHost* embedder_render_widget_host, ++ WebContentsView* web_contents_view) { ++ return web_contents_view->CreateViewForWidget( ++ render_widget_host, ++ !!embedder_render_widget_host); ++} ++ + void RenderWidgetHostViewBase::ProcessMouseEvent( + const blink::WebMouseEvent& event, + const ui::LatencyInfo& latency) { +diff --git a/content/browser/renderer_host/render_widget_host_view_base.h b/content/browser/renderer_host/render_widget_host_view_base.h +index 8e391207a8a7..d3637c82aba9 100644 +--- a/content/browser/renderer_host/render_widget_host_view_base.h ++++ b/content/browser/renderer_host/render_widget_host_view_base.h +@@ -21,8 +21,10 @@ + #include "components/viz/common/surfaces/scoped_surface_id_allocator.h" + #include "components/viz/common/surfaces/surface_id.h" + #include "content/browser/renderer_host/event_with_latency_info.h" ++#include "content/browser/web_contents/web_contents_view.h" + #include "content/common/content_export.h" + #include "content/public/browser/render_frame_metadata_provider.h" ++#include "content/public/browser/render_widget_host.h" + #include "content/public/browser/render_widget_host_view.h" + #include "content/public/common/input_event_ack_state.h" + #include "content/public/common/screen_info.h" +@@ -79,10 +81,12 @@ class BrowserAccessibilityManager; + class CursorManager; + class RenderWidgetHostImpl; + class RenderWidgetHostViewBaseObserver; ++class RenderWidgetHostViewGuest; + class SyntheticGestureTarget; + class TextInputManager; + class TouchSelectionControllerClientManager; + class WebContentsAccessibility; ++class WebContentsView; + class WebCursor; + struct TextInputState; + +@@ -124,6 +128,9 @@ class CONTENT_EXPORT RenderWidgetHostViewBase : public RenderWidgetHostView, + float GetDeviceScaleFactor() const final; + TouchSelectionControllerClientManager* + GetTouchSelectionControllerClientManager() override; ++ ++ virtual void InitAsGuest(RenderWidgetHostView* parent_host_view, ++ RenderWidgetHostViewGuest* guest_view) {} + + // This only needs to be overridden by RenderWidgetHostViewBase subclasses + // that handle content embedded within other RenderWidgetHostViews. +@@ -318,6 +325,11 @@ class CONTENT_EXPORT RenderWidgetHostViewBase : public RenderWidgetHostView, + virtual void ProcessGestureEvent(const blink::WebGestureEvent& event, + const ui::LatencyInfo& latency); + ++ virtual RenderWidgetHostViewBase* CreateViewForWidget( ++ RenderWidgetHost* render_widget_host, ++ RenderWidgetHost* embedder_render_widget_host, ++ WebContentsView* web_contents_view); ++ + // Transform a point that is in the coordinate space of a Surface that is + // embedded within the RenderWidgetHostViewBase's Surface to the + // coordinate space of an embedding, or embedded, Surface. Typically this diff --git a/patches/common/chromium/render_widget_host_view_mac.patch b/patches/common/chromium/render_widget_host_view_mac.patch new file mode 100644 index 00000000000..3a9e635fa91 --- /dev/null +++ b/patches/common/chromium/render_widget_host_view_mac.patch @@ -0,0 +1,102 @@ +diff --git a/content/browser/renderer_host/render_widget_host_view_mac.mm b/content/browser/renderer_host/render_widget_host_view_mac.mm +index 6a161f0f36c6..349bc78976ad 100644 +--- a/content/browser/renderer_host/render_widget_host_view_mac.mm ++++ b/content/browser/renderer_host/render_widget_host_view_mac.mm +@@ -48,6 +48,7 @@ + #include "ui/gfx/geometry/dip_util.h" + #include "ui/gfx/mac/coordinate_conversion.h" + #include "ui/gl/gl_switches.h" ++#include "ui/gl/gpu_switching_manager.h" + + using blink::WebInputEvent; + using blink::WebMouseEvent; +@@ -1112,6 +1113,12 @@ void RenderWidgetHostViewMac::SetBackgroundColor(SkColor color) { + DCHECK(SkColorGetA(color) == SK_AlphaOPAQUE || + SkColorGetA(color) == SK_AlphaTRANSPARENT); + bool opaque = SkColorGetA(color) == SK_AlphaOPAQUE; ++ if (opaque) { ++ bool wantsTransparent = ui::GpuSwitchingManager::UseTransparent() || ++ ([cocoa_view() window] && ![[cocoa_view() window] isOpaque]); ++ if (wantsTransparent) ++ opaque = NO; ++ } + if (background_is_opaque_ != opaque) { + background_is_opaque_ = opaque; + if (host()) +diff --git a/content/browser/renderer_host/render_widget_host_view_cocoa.mm b/content/browser/renderer_host/render_widget_host_view_cocoa.mm +index c7ad6fa8c75f..bdfabc1061bb 100644 +--- a/content/browser/renderer_host/render_widget_host_view_cocoa.mm ++++ b/content/browser/renderer_host/render_widget_host_view_cocoa.mm +@@ -178,6 +178,11 @@ void ExtractUnderlines(NSAttributedString* string, + + } // namespace + ++@interface NSWindow (AtomCustomMethods) ++- (BOOL)acceptsFirstMouse; ++- (BOOL)disableAutoHideCursor; ++@end ++ + // These are not documented, so use only after checking -respondsToSelector:. + @interface NSApplication (UndocumentedSpeechMethods) + - (void)speakString:(NSString*)string; +@@ -355,6 +360,9 @@ void ExtractUnderlines(NSAttributedString* string, + } + + - (BOOL)acceptsFirstMouse:(NSEvent*)theEvent { ++ if ([self.window respondsToSelector:@selector(acceptsFirstMouse)] && ++ [self.window acceptsFirstMouse]) ++ return YES; + return [self acceptsMouseEventsWhenInactive]; + } + +@@ -555,6 +563,7 @@ void ExtractUnderlines(NSAttributedString* string, + if (EventIsReservedBySystem(theEvent)) + return NO; + ++#if 0 + // If we return |NO| from this function, cocoa will send the key event to + // the menu and only if the menu does not process the event to |keyDown:|. We + // want to send the event to a renderer _before_ sending it to the menu, so +@@ -568,6 +577,7 @@ void ExtractUnderlines(NSAttributedString* string, + DCHECK(![[NSApp mainMenu] performKeyEquivalent:theEvent]); + return NO; + } ++#endif + + // Command key combinations are sent via performKeyEquivalent rather than + // keyDown:. We just forward this on and if WebCore doesn't want to handle +@@ -664,6 +674,10 @@ void ExtractUnderlines(NSAttributedString* string, + eventType == NSKeyDown && + !(modifierFlags & NSCommandKeyMask); + ++ if ([theEvent.window respondsToSelector:@selector(disableAutoHideCursor)] && ++ [theEvent.window disableAutoHideCursor]) ++ shouldAutohideCursor = NO; ++ + // We only handle key down events and just simply forward other events. + if (eventType != NSKeyDown) { + client_->OnNSViewForwardKeyboardEvent(event, latency_info); +@@ -1425,9 +1439,11 @@ void ExtractUnderlines(NSAttributedString* string, + // Since this implementation doesn't have to wait any IPC calls, this doesn't + // make any key-typing jank. --hbono 7/23/09 + // ++#ifndef MAS_BUILD + extern "C" { + extern NSString* NSTextInputReplacementRangeAttributeName; + } ++#endif + + - (NSArray*)validAttributesForMarkedText { + // This code is just copied from WebKit except renaming variables. +@@ -1436,7 +1452,10 @@ extern NSString* NSTextInputReplacementRangeAttributeName; + initWithObjects:NSUnderlineStyleAttributeName, + NSUnderlineColorAttributeName, + NSMarkedClauseSegmentAttributeName, +- NSTextInputReplacementRangeAttributeName, nil]); ++#ifndef MAS_BUILD ++ NSTextInputReplacementRangeAttributeName, ++#endif ++ nil]); + } + return validAttributesForMarkedText_.get(); + } diff --git a/patches/common/chromium/resource_file_conflict.patch b/patches/common/chromium/resource_file_conflict.patch new file mode 100644 index 00000000000..88ac15f6ffa --- /dev/null +++ b/patches/common/chromium/resource_file_conflict.patch @@ -0,0 +1,24 @@ +diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn +index fbcf20c..d2173e2 100644 +--- a/chrome/BUILD.gn ++++ b/chrome/BUILD.gn +@@ -1656,6 +1656,11 @@ if (is_chrome_branded && !is_android) { + } + } + ++if (is_electron_gn_build) { ++ group("packed_resources") { ++ public_deps = [ "//electron:packed_resources" ] ++ } ++} else { + chrome_paks("packed_resources") { + if (is_mac) { + output_dir = "$root_gen_dir/repack" +@@ -1677,6 +1682,7 @@ chrome_paks("packed_resources") { + ] + } + } ++} + + repack("browser_tests_pak") { + sources = [ diff --git a/patches/common/chromium/scoped_clipboard_writer.patch b/patches/common/chromium/scoped_clipboard_writer.patch new file mode 100644 index 00000000000..168d5d57ad0 --- /dev/null +++ b/patches/common/chromium/scoped_clipboard_writer.patch @@ -0,0 +1,57 @@ +diff --git a/ui/base/clipboard/scoped_clipboard_writer.cc b/ui/base/clipboard/scoped_clipboard_writer.cc +index 6850cd460b1d..6d652cca59b4 100644 +--- a/ui/base/clipboard/scoped_clipboard_writer.cc ++++ b/ui/base/clipboard/scoped_clipboard_writer.cc +@@ -102,17 +102,16 @@ void ScopedClipboardWriter::WriteImage(const SkBitmap& bitmap) { + objects_[Clipboard::CBF_SMBITMAP] = parameters; + } + +-void ScopedClipboardWriter::WritePickledData( +- const base::Pickle& pickle, +- const Clipboard::FormatType& format) { ++void ScopedClipboardWriter::WriteData(const char* data, ++ int size, ++ const Clipboard::FormatType& format) { + std::string format_string = format.Serialize(); + Clipboard::ObjectMapParam format_parameter(format_string.begin(), + format_string.end()); + Clipboard::ObjectMapParam data_parameter; + +- data_parameter.resize(pickle.size()); +- memcpy(const_cast(&data_parameter.front()), +- pickle.data(), pickle.size()); ++ data_parameter.resize(size); ++ memcpy(const_cast(&data_parameter.front()), data, size); + + Clipboard::ObjectMapParams parameters; + parameters.push_back(format_parameter); +@@ -121,6 +121,13 @@ void ScopedClipboardWriter::WritePickledData( + objects_[Clipboard::CBF_DATA] = parameters; + } + ++void ScopedClipboardWriter::WritePickledData( ++ const base::Pickle& pickle, ++ const Clipboard::FormatType& format) { ++ WriteData(reinterpret_cast(pickle.data()), pickle.size(), ++ format); ++} ++ + void ScopedClipboardWriter::Reset() { + objects_.clear(); + bitmap_.reset(); +diff --git a/ui/base/clipboard/scoped_clipboard_writer.h b/ui/base/clipboard/scoped_clipboard_writer.h +index a7e064561ca9..d5a1b76bc6a7 100644 +--- a/ui/base/clipboard/scoped_clipboard_writer.h ++++ b/ui/base/clipboard/scoped_clipboard_writer.h +@@ -61,6 +61,11 @@ class UI_BASE_EXPORT ScopedClipboardWriter { + // Used by WebKit to determine whether WebKit wrote the clipboard last + void WriteWebSmartPaste(); + ++ // Adds arbitrary data to clipboard. ++ void WriteData(const char* data, ++ int size, ++ const Clipboard::FormatType& format); ++ + // Adds arbitrary pickled data to clipboard. + void WritePickledData(const base::Pickle& pickle, + const Clipboard::FormatType& format); diff --git a/patches/common/chromium/scroll_bounce_flag.patch b/patches/common/chromium/scroll_bounce_flag.patch new file mode 100644 index 00000000000..b405a951abd --- /dev/null +++ b/patches/common/chromium/scroll_bounce_flag.patch @@ -0,0 +1,13 @@ +diff --git a/content/renderer/render_thread_impl.cc b/content/renderer/render_thread_impl.cc +index 81d3f80..a8c4a57 100644 +--- a/content/renderer/render_thread_impl.cc ++++ b/content/renderer/render_thread_impl.cc +@@ -1737,7 +1737,7 @@ bool RenderThreadImpl::IsGpuMemoryBufferCompositorResourcesEnabled() { + } + + bool RenderThreadImpl::IsElasticOverscrollEnabled() { +- return is_elastic_overscroll_enabled_; ++ return base::CommandLine::ForCurrentProcess()->HasSwitch("scroll-bounce"); + } + + scoped_refptr diff --git a/patches/common/chromium/ssl_security_state_tab_helper.patch b/patches/common/chromium/ssl_security_state_tab_helper.patch new file mode 100644 index 00000000000..012ee0031fc --- /dev/null +++ b/patches/common/chromium/ssl_security_state_tab_helper.patch @@ -0,0 +1,91 @@ +diff --git a/chrome/browser/ssl/security_state_tab_helper.cc b/chrome/browser/ssl/security_state_tab_helper.cc +index a73442a5476c..6cd7ae78b814 100644 +--- a/chrome/browser/ssl/security_state_tab_helper.cc ++++ b/chrome/browser/ssl/security_state_tab_helper.cc +@@ -10,15 +10,21 @@ + #include "base/metrics/histogram_macros.h" + #include "base/time/time.h" + #include "build/build_config.h" ++#if 0 + #include "chrome/browser/browser_process.h" + #include "chrome/browser/profiles/profile.h" + #include "chrome/browser/safe_browsing/safe_browsing_service.h" + #include "chrome/browser/safe_browsing/ui_manager.h" ++#endif + #include "components/prefs/pref_service.h" ++#if 0 + #include "components/safe_browsing/features.h" ++#endif + #include "components/security_state/content/content_utils.h" + #include "components/ssl_config/ssl_config_prefs.h" ++#if 0 + #include "components/toolbar/toolbar_field_trial.h" ++#endif + #include "content/public/browser/browser_context.h" + #include "content/public/browser/navigation_entry.h" + #include "content/public/browser/navigation_handle.h" +@@ -37,7 +43,7 @@ + #include "chrome/browser/chromeos/policy/policy_cert_service_factory.h" + #endif // defined(OS_CHROMEOS) + +-#if defined(SAFE_BROWSING_DB_LOCAL) ++#if 0 + #include "chrome/browser/safe_browsing/chrome_password_protection_service.h" + #endif + +@@ -59,7 +65,9 @@ void RecordSecurityLevel(const security_state::SecurityInfo& security_info) { + + DEFINE_WEB_CONTENTS_USER_DATA_KEY(SecurityStateTabHelper); + ++#if 0 + using safe_browsing::SafeBrowsingUIManager; ++#endif + + SecurityStateTabHelper::SecurityStateTabHelper( + content::WebContents* web_contents) +@@ -67,8 +75,11 @@ SecurityStateTabHelper::SecurityStateTabHelper( + logged_http_warning_on_current_navigation_(false), + is_incognito_(false) { + content::BrowserContext* context = web_contents->GetBrowserContext(); +- if (context->IsOffTheRecord() && +- !Profile::FromBrowserContext(context)->IsGuestSession()) { ++ if (context->IsOffTheRecord() ++#if 0 ++ && !Profile::FromBrowserContext(context)->IsGuestSession() ++#endif ++ ) { + is_incognito_ = true; + } + } +@@ -150,6 +161,7 @@ void SecurityStateTabHelper::DidFinishNavigation( + UMA_HISTOGRAM_BOOLEAN("interstitial.ssl.visited_site_after_warning", true); + } + ++#if 0 + // Security indicator UI study (https://crbug.com/803501): Show a message in + // the console to reduce developer confusion about the experimental UI + // treatments for HTTPS pages with EV certificates. +@@ -177,6 +189,7 @@ void SecurityStateTabHelper::DidFinishNavigation( + "Validation is still valid."); + } + } ++#endif + } + + void SecurityStateTabHelper::DidChangeVisibleSecurityState() { +@@ -250,6 +263,7 @@ SecurityStateTabHelper::GetMaliciousContentStatus() const { + web_contents()->GetController().GetVisibleEntry(); + if (!entry) + return security_state::MALICIOUS_CONTENT_STATUS_NONE; ++#if 0 + safe_browsing::SafeBrowsingService* sb_service = + g_browser_process->safe_browsing_service(); + if (!sb_service) +@@ -301,6 +315,7 @@ SecurityStateTabHelper::GetMaliciousContentStatus() const { + break; + } + } ++#endif + return security_state::MALICIOUS_CONTENT_STATUS_NONE; + } + diff --git a/patches/common/chromium/statically_build_power_save_blocker.patch b/patches/common/chromium/statically_build_power_save_blocker.patch new file mode 100644 index 00000000000..fb383cb9e29 --- /dev/null +++ b/patches/common/chromium/statically_build_power_save_blocker.patch @@ -0,0 +1,21 @@ +diff --git a/services/device/wake_lock/power_save_blocker/BUILD.gn b/services/device/wake_lock/power_save_blocker/BUILD.gn +index e04629ca1a93..299e6efd75f9 100644 +--- a/services/device/wake_lock/power_save_blocker/BUILD.gn ++++ b/services/device/wake_lock/power_save_blocker/BUILD.gn +@@ -9,7 +9,7 @@ if (is_android) { + import("//build/config/android/rules.gni") + } + +-source_set("power_save_blocker") { ++static_library("power_save_blocker") { + visibility = [ + # //remoting runs in a separate process which is outside of the context of + # the ServiceManager-based world. Instead of embedding a Service Manager +@@ -18,6 +18,7 @@ source_set("power_save_blocker") { + "//remoting/host:*", + "//remoting/host/win:*", + "//services/device/wake_lock:*", ++ "//electron:*", + ] + + sources = [ diff --git a/patches/common/chromium/stream_resource_handler.patch b/patches/common/chromium/stream_resource_handler.patch new file mode 100644 index 00000000000..a14ca699baf --- /dev/null +++ b/patches/common/chromium/stream_resource_handler.patch @@ -0,0 +1,21 @@ +diff --git a/content/browser/loader/stream_resource_handler.h b/content/browser/loader/stream_resource_handler.h +index 9f69994..ae8d1630 100644 +--- a/content/browser/loader/stream_resource_handler.h ++++ b/content/browser/loader/stream_resource_handler.h +@@ -11,6 +11,7 @@ + #include "base/memory/ref_counted.h" + #include "content/browser/loader/resource_handler.h" + #include "content/browser/loader/stream_writer.h" ++#include "content/common/content_export.h" + + namespace net { + class URLRequest; +@@ -22,7 +23,7 @@ class ResourceController; + class StreamRegistry; + + // Redirect this resource to a stream. +-class StreamResourceHandler : public ResourceHandler { ++class CONTENT_EXPORT StreamResourceHandler : public ResourceHandler { + public: + // |origin| will be used to construct the URL for the Stream. See + // WebCore::BlobURL and and WebCore::SecurityOrigin in Blink to understand diff --git a/patches/common/chromium/sysroot.patch b/patches/common/chromium/sysroot.patch new file mode 100644 index 00000000000..52b862b0600 --- /dev/null +++ b/patches/common/chromium/sysroot.patch @@ -0,0 +1,126 @@ +diff --git a/build/config/sysroot.gni b/build/config/sysroot.gni +index d5daf2df2e41..46999e2e2198 100644 +--- a/build/config/sysroot.gni ++++ b/build/config/sysroot.gni +@@ -32,17 +32,17 @@ if (current_os == target_os && current_cpu == target_cpu && + # By default build against a sysroot image downloaded from Cloud Storage + # during gclient runhooks. + if (current_cpu == "x64") { +- sysroot = "$target_sysroot_dir/debian_sid_amd64-sysroot" ++ sysroot = "$target_sysroot_dir/debian_stretch_amd64-sysroot" + } else if (current_cpu == "x86") { +- sysroot = "$target_sysroot_dir/debian_sid_i386-sysroot" ++ sysroot = "$target_sysroot_dir/debian_stretch_i386-sysroot" + } else if (current_cpu == "mipsel") { +- sysroot = "$target_sysroot_dir/debian_sid_mips-sysroot" ++ sysroot = "$target_sysroot_dir/debian_stretch_mips-sysroot" + } else if (current_cpu == "mips64el") { +- sysroot = "$target_sysroot_dir/debian_sid_mips64el-sysroot" ++ sysroot = "$target_sysroot_dir/debian_stretch_mips64el-sysroot" + } else if (current_cpu == "arm") { +- sysroot = "$target_sysroot_dir/debian_sid_arm-sysroot" ++ sysroot = "$target_sysroot_dir/debian_stretch_arm-sysroot" + } else if (current_cpu == "arm64") { +- sysroot = "$target_sysroot_dir/debian_sid_arm64-sysroot" ++ sysroot = "$target_sysroot_dir/debian_stretch_arm64-sysroot" + } else { + assert(false, "No linux sysroot for cpu: $target_cpu") + } +diff --git a/build/linux/sysroot_scripts/install-sysroot.py b/build/linux/sysroot_scripts/install-sysroot.py +index 58f09950d844..53500a0853a6 100755 +--- a/build/linux/sysroot_scripts/install-sysroot.py ++++ b/build/linux/sysroot_scripts/install-sysroot.py +@@ -31,8 +31,8 @@ import urllib2 + + SCRIPT_DIR = os.path.dirname(os.path.abspath(__file__)) + +-URL_PREFIX = 'https://commondatastorage.googleapis.com' +-URL_PATH = 'chrome-linux-sysroot/toolchain' ++URL_PREFIX = 'http://s3.amazonaws.com' ++URL_PATH = 'gh-contractor-zcbenz/toolchain' + + VALID_ARCHS = ('arm', 'arm64', 'i386', 'amd64', 'mips', 'mips64el') + +@@ -43,7 +43,7 @@ ARCH_TRANSLATIONS = { + 'mips64': 'mips64el', + } + +-DEFAULT_TARGET_PLATFORM = 'sid' ++DEFAULT_TARGET_PLATFORM = 'stretch' + + class Error(Exception): + pass +diff --git a/build/linux/sysroot_scripts/sysroots.json b/build/linux/sysroot_scripts/sysroots.json +index 48a1d36f0609..91ef1417a1bf 100644 +--- a/build/linux/sysroot_scripts/sysroots.json ++++ b/build/linux/sysroot_scripts/sysroots.json +@@ -1,38 +1,38 @@ + { +- "sid_amd64": { +- "Revision": "15b7efb900d75f7316c6e713e80f87b9904791b1", +- "Sha1Sum": "85ac8d5e0f6cff99fc323fd3d29cb73e2aa970e2", +- "SysrootDir": "debian_sid_amd64-sysroot", +- "Tarball": "debian_sid_amd64_sysroot.tar.xz" ++ "stretch_amd64": { ++ "Revision": "02772eaba5440a79c6bd2d9cb7e42fa836950366", ++ "Sha1Sum": "69457fddca3500e2dde124f77f8382b0a18d765e", ++ "SysrootDir": "debian_stretch_amd64-sysroot", ++ "Tarball": "debian_stretch_amd64_sysroot.tgz" + }, +- "sid_arm": { +- "Revision": "15b7efb900d75f7316c6e713e80f87b9904791b1", +- "Sha1Sum": "ed31924757f11885a21793dc4b928d07ab25740c", +- "SysrootDir": "debian_sid_arm-sysroot", +- "Tarball": "debian_sid_arm_sysroot.tar.xz" ++ "stretch_arm": { ++ "Revision": "02772eaba5440a79c6bd2d9cb7e42fa836950366", ++ "Sha1Sum": "3e880f69177992ce02b05deeac619f7591b30287", ++ "SysrootDir": "debian_stretch_arm-sysroot", ++ "Tarball": "debian_stretch_arm_sysroot.tgz" + }, +- "sid_arm64": { +- "Revision": "15b7efb900d75f7316c6e713e80f87b9904791b1", +- "Sha1Sum": "b9447285e58c5260bd9fa2737d1f0d1f82156738", +- "SysrootDir": "debian_sid_arm64-sysroot", +- "Tarball": "debian_sid_arm64_sysroot.tar.xz" ++ "stretch_arm64": { ++ "Revision": "02772eaba5440a79c6bd2d9cb7e42fa836950366", ++ "Sha1Sum": "8fd58c7d4b38fa3c6785573c6310cf6ca6c88312", ++ "SysrootDir": "debian_stretch_arm64-sysroot", ++ "Tarball": "debian_stretch_arm64_sysroot.tgz" + }, +- "sid_i386": { +- "Revision": "15b7efb900d75f7316c6e713e80f87b9904791b1", +- "Sha1Sum": "f09856d93f39e8df84ffd9c04881f44e6cbc0508", +- "SysrootDir": "debian_sid_i386-sysroot", +- "Tarball": "debian_sid_i386_sysroot.tar.xz" ++ "stretch_i386": { ++ "Revision": "02772eaba5440a79c6bd2d9cb7e42fa836950366", ++ "Sha1Sum": "1bd14db5eb0466064659126d398b38220013fb38", ++ "SysrootDir": "debian_stretch_i386-sysroot", ++ "Tarball": "debian_stretch_i386_sysroot.tgz" + }, +- "sid_mips": { +- "Revision": "15b7efb900d75f7316c6e713e80f87b9904791b1", +- "Sha1Sum": "90586b566b567b2bcf49e7fd112f0c8189bbd07b", +- "SysrootDir": "debian_sid_mips-sysroot", +- "Tarball": "debian_sid_mips_sysroot.tar.xz" ++ "stretch_mips": { ++ "Revision": "02772eaba5440a79c6bd2d9cb7e42fa836950366", ++ "Sha1Sum": "285751660ffab14e6d052c8ddb5c90752a51704d", ++ "SysrootDir": "debian_stretch_mips-sysroot", ++ "Tarball": "debian_stretch_mips_sysroot.tgz" + }, +- "sid_mips64el": { +- "Revision": "15b7efb900d75f7316c6e713e80f87b9904791b1", +- "Sha1Sum": "f90c3b81485ffebb283afddb1a72bc61e14c593d", +- "SysrootDir": "debian_sid_mips64el-sysroot", +- "Tarball": "debian_sid_mips64el_sysroot.tar.xz" +- } ++ "stretch_mips64el": { ++ "Revision": "02772eaba5440a79c6bd2d9cb7e42fa836950366", ++ "Sha1Sum": "23f51f29bc35a550092dde41dc823780fdb50f9e", ++ "SysrootDir": "debian_stretch_mips64el-sysroot", ++ "Tarball": "debian_stretch_mips64el_sysroot.tgz" ++ } + } diff --git a/patches/common/chromium/thread_capabilities.patch b/patches/common/chromium/thread_capabilities.patch new file mode 100644 index 00000000000..97feca57285 --- /dev/null +++ b/patches/common/chromium/thread_capabilities.patch @@ -0,0 +1,15 @@ +diff --git a/sandbox/linux/services/credentials.cc b/sandbox/linux/services/credentials.cc +index 50a109e..3ee9159 100644 +--- a/sandbox/linux/services/credentials.cc ++++ b/sandbox/linux/services/credentials.cc +@@ -358,8 +358,10 @@ pid_t Credentials::ForkAndDropCapabilitiesInChild() { + return pid; + } + ++#if 0 + // Since we just forked, we are single threaded. + PCHECK(DropAllCapabilitiesOnCurrentThread()); ++#endif + return 0; + } + diff --git a/patches/common/chromium/use_transparent_window.patch b/patches/common/chromium/use_transparent_window.patch new file mode 100644 index 00000000000..1dc8a9be400 --- /dev/null +++ b/patches/common/chromium/use_transparent_window.patch @@ -0,0 +1,48 @@ +diff --git a/ui/gl/gpu_switching_manager.cc b/ui/gl/gpu_switching_manager.cc +index be7156465809..cee3b1af3dc5 100644 +--- a/ui/gl/gpu_switching_manager.cc ++++ b/ui/gl/gpu_switching_manager.cc +@@ -4,6 +4,12 @@ + + #include "ui/gl/gpu_switching_manager.h" + ++namespace { ++ ++bool g_use_transparent = false; ++ ++} // namespace ++ + namespace ui { + + // static +@@ -11,6 +17,16 @@ GpuSwitchingManager* GpuSwitchingManager::GetInstance() { + return base::Singleton::get(); + } + ++// static ++void GpuSwitchingManager::SetTransparent(bool transparent) { ++ g_use_transparent = transparent; ++} ++ ++// static ++bool GpuSwitchingManager::UseTransparent() { ++ return g_use_transparent; ++} ++ + GpuSwitchingManager::GpuSwitchingManager() {} + + GpuSwitchingManager::~GpuSwitchingManager() {} +diff --git a/ui/gl/gpu_switching_manager.h b/ui/gl/gpu_switching_manager.h +index 4308bbed9398..a7cafcfccdff 100644 +--- a/ui/gl/gpu_switching_manager.h ++++ b/ui/gl/gpu_switching_manager.h +@@ -18,6 +18,9 @@ class GL_EXPORT GpuSwitchingManager { + // Getter for the singleton. This will return NULL on failure. + static GpuSwitchingManager* GetInstance(); + ++ static void SetTransparent(bool transparent); ++ static bool UseTransparent(); ++ + void AddObserver(GpuSwitchingObserver* observer); + void RemoveObserver(GpuSwitchingObserver* observer); + diff --git a/patches/common/chromium/v8_context_snapshot_generator.patch b/patches/common/chromium/v8_context_snapshot_generator.patch new file mode 100644 index 00000000000..576bab5e5b8 --- /dev/null +++ b/patches/common/chromium/v8_context_snapshot_generator.patch @@ -0,0 +1,12 @@ +diff --git a/tools/v8_context_snapshot/BUILD.gn b/tools/v8_context_snapshot/BUILD.gn +index d6691a527f25..000105b86f53 100644 +--- a/tools/v8_context_snapshot/BUILD.gn ++++ b/tools/v8_context_snapshot/BUILD.gn +@@ -105,6 +105,7 @@ if (use_v8_context_snapshot) { + configs += [ + "//v8:external_startup_data", + ":disable_icf", ++ "//electron/build/config:build_time_executable" + ] + } + } diff --git a/patches/common/chromium/web_contents.patch b/patches/common/chromium/web_contents.patch new file mode 100644 index 00000000000..c207586ed14 --- /dev/null +++ b/patches/common/chromium/web_contents.patch @@ -0,0 +1,115 @@ +diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc +index 018534073da1..48f3d0e7343b 100644 +--- a/content/browser/web_contents/web_contents_impl.cc ++++ b/content/browser/web_contents/web_contents_impl.cc +@@ -1759,6 +1759,12 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params) { + std::string unique_name; + frame_tree_.root()->SetFrameName(params.main_frame_name, unique_name); + ++ if (params.view && params.delegate_view) { ++ view_.reset(params.view); ++ render_view_host_delegate_view_ = params.delegate_view; ++ } ++ ++ if (!view_) { + WebContentsViewDelegate* delegate = + GetContentClient()->browser()->GetWebContentsViewDelegate(this); + +@@ -1774,6 +1780,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params) { + &render_view_host_delegate_view_); + } + } ++ } // !view_ + CHECK(render_view_host_delegate_view_); + CHECK(view_.get()); + +diff --git a/content/browser/web_contents/web_contents_view_guest.cc b/content/browser/web_contents/web_contents_view_guest.cc +index 699570cc1390..454830098cb9 100644 +--- a/content/browser/web_contents/web_contents_view_guest.cc ++++ b/content/browser/web_contents/web_contents_view_guest.cc +@@ -67,21 +67,27 @@ gfx::NativeWindow WebContentsViewGuest::GetTopLevelNativeWindow() const { + + void WebContentsViewGuest::OnGuestAttached(WebContentsView* parent_view) { + #if defined(USE_AURA) ++ if (!platform_view_->GetNativeView()) ++ return; + // In aura, ScreenPositionClient doesn't work properly if we do + // not have the native view associated with this WebContentsViewGuest in the + // view hierarchy. We add this view as embedder's child here. + // This would go in WebContentsViewGuest::CreateView, but that is too early to + // access embedder_web_contents(). Therefore, we do it here. + if (!base::FeatureList::IsEnabled(features::kMash)) +- parent_view->GetNativeView()->AddChild(platform_view_->GetNativeView()); ++ if (parent_view->GetNativeView() != platform_view_->GetNativeView()) ++ parent_view->GetNativeView()->AddChild(platform_view_->GetNativeView()); + #endif // defined(USE_AURA) + } + + void WebContentsViewGuest::OnGuestDetached(WebContentsView* old_parent_view) { + #if defined(USE_AURA) ++ if (!platform_view_->GetNativeView()) ++ return; + if (!base::FeatureList::IsEnabled(features::kMash)) { +- old_parent_view->GetNativeView()->RemoveChild( +- platform_view_->GetNativeView()); ++ if (old_parent_view->GetNativeView() != platform_view_->GetNativeView()) ++ old_parent_view->GetNativeView()->RemoveChild( ++ platform_view_->GetNativeView()); + } + #endif // defined(USE_AURA) + } +@@ -146,11 +152,22 @@ RenderWidgetHostViewBase* WebContentsViewGuest::CreateViewForWidget( + render_widget_host->GetView()); + } + ++ RenderWidgetHost* embedder_render_widget_host = ++ guest_->embedder_web_contents()->GetRenderViewHost()->GetWidget(); ++ RenderWidgetHostViewBase* embedder_render_widget_host_view = ++ static_cast( ++ embedder_render_widget_host->GetView()); + RenderWidgetHostViewBase* platform_widget = +- platform_view_->CreateViewForWidget(render_widget_host, true); +- +- return RenderWidgetHostViewGuest::Create(render_widget_host, guest_, +- platform_widget->GetWeakPtr()); ++ embedder_render_widget_host_view->CreateViewForWidget( ++ render_widget_host, ++ embedder_render_widget_host, ++ platform_view_.get()); ++ RenderWidgetHostViewGuest* guest_view = RenderWidgetHostViewGuest::Create( ++ render_widget_host, guest_, platform_widget->GetWeakPtr()); ++ platform_widget->InitAsGuest(embedder_render_widget_host->GetView(), ++ guest_view); ++ ++ return guest_view; + } + + RenderWidgetHostViewBase* WebContentsViewGuest::CreateViewForPopupWidget( +diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h +index a13db5f4dd61..621124decfdc 100644 +--- a/content/public/browser/web_contents.h ++++ b/content/public/browser/web_contents.h +@@ -69,9 +69,12 @@ class BrowserPluginGuestDelegate; + class InterstitialPage; + class RenderFrameHost; + class RenderViewHost; ++class RenderViewHostDelegateView; + class RenderWidgetHost; + class RenderWidgetHostView; ++class RenderWidgetHostViewBase; + class WebContentsDelegate; ++class WebContentsView; + struct CustomContextMenuContext; + struct DropData; + struct Manifest; +@@ -172,6 +175,10 @@ class WebContents : public PageNavigator, + // navigation requires a dedicated or privileged process, such as a WebUI. + bool initialize_renderer; + ++ // Optionally specify the view and delegate view. ++ content::WebContentsView* view = nullptr; ++ content::RenderViewHostDelegateView* delegate_view = nullptr; ++ + // Sandboxing flags set on the new WebContents. + blink::WebSandboxFlags starting_sandbox_flags; + }; diff --git a/patches/common/chromium/webgl_context_attributes.patch b/patches/common/chromium/webgl_context_attributes.patch new file mode 100644 index 00000000000..2ca99ba0167 --- /dev/null +++ b/patches/common/chromium/webgl_context_attributes.patch @@ -0,0 +1,111 @@ +diff --git a/content/renderer/renderer_blink_platform_impl.cc b/content/renderer/renderer_blink_platform_impl.cc +index 0affacaa0294..0c321d51364d 100644 +--- a/content/renderer/renderer_blink_platform_impl.cc ++++ b/content/renderer/renderer_blink_platform_impl.cc +@@ -1136,8 +1136,10 @@ RendererBlinkPlatformImpl::CreateOffscreenGraphicsContext3DProvider( + attributes.sample_buffers = 0; + attributes.bind_generates_resource = false; + attributes.enable_raster_interface = web_attributes.enable_raster_interface; +- // Prefer discrete GPU for WebGL. +- attributes.gpu_preference = gl::PreferDiscreteGpu; ++ ++ attributes.gpu_preference = web_attributes.prefer_integrated_gpu ++ ? gl::PreferIntegratedGpu ++ : gl::PreferDiscreteGpu; + + attributes.fail_if_major_perf_caveat = + web_attributes.fail_if_major_performance_caveat; +diff --git a/third_party/blink/renderer/core/html/canvas/canvas_context_creation_attributes_core.h b/third_party/blink/renderer/core/html/canvas/canvas_context_creation_attributes_core.h +index ca4543a10e69..a1f5e5c9f906 100644 +--- a/third_party/blink/renderer/core/html/canvas/canvas_context_creation_attributes_core.h ++++ b/third_party/blink/renderer/core/html/canvas/canvas_context_creation_attributes_core.h +@@ -30,6 +30,7 @@ class CORE_EXPORT CanvasContextCreationAttributesCore { + String pixel_format = "8-8-8-8"; + bool premultiplied_alpha = true; + bool preserve_drawing_buffer = false; ++ String power_preference = "default"; + bool stencil = false; + + // This attribute is of type XRDevice, defined in modules/xr/XRDevice.h +diff --git a/third_party/blink/renderer/modules/canvas/htmlcanvas/canvas_context_creation_attributes_module.idl b/third_party/blink/renderer/modules/canvas/htmlcanvas/canvas_context_creation_attributes_module.idl +index 7419bb20d316..5b04af00fab4 100644 +--- a/third_party/blink/renderer/modules/canvas/htmlcanvas/canvas_context_creation_attributes_module.idl ++++ b/third_party/blink/renderer/modules/canvas/htmlcanvas/canvas_context_creation_attributes_module.idl +@@ -28,6 +28,12 @@ enum CanvasPixelFormat { + "float16", + }; + ++enum CanvasPowerPreference { ++ "default", ++ "low-power", ++ "high-performance", ++}; ++ + [PermissiveDictionaryConversion] + dictionary CanvasContextCreationAttributesModule { + // This is an experimental feature, but it is not hidden behind a flag in +@@ -47,6 +47,7 @@ dictionary CanvasContextCreationAttributesModule { + boolean antialias = true; + boolean premultipliedAlpha = true; + boolean preserveDrawingBuffer = false; ++ CanvasPowerPreference powerPreference = "default"; + boolean failIfMajorPerformanceCaveat = false; + [OriginTrialEnabled=WebXR] XRDevice compatibleXRDevice = null; + }; +diff --git a/third_party/blink/renderer/modules/webgl/webgl_context_attribute_helpers.cc b/third_party/blink/renderer/modules/webgl/webgl_context_attribute_helpers.cc +index 332fa9fb0547..e8fae4b01c39 100644 +--- a/third_party/blink/renderer/modules/webgl/webgl_context_attribute_helpers.cc ++++ b/third_party/blink/renderer/modules/webgl/webgl_context_attribute_helpers.cc +@@ -18,6 +18,7 @@ WebGLContextAttributes ToWebGLContextAttributes( + result.setAntialias(attrs.antialias); + result.setPremultipliedAlpha(attrs.premultiplied_alpha); + result.setPreserveDrawingBuffer(attrs.preserve_drawing_buffer); ++ result.setPowerPreference(attrs.power_preference); + result.setFailIfMajorPerformanceCaveat( + attrs.fail_if_major_performance_caveat); + result.setCompatibleXRDevice( +@@ -30,6 +30,7 @@ Platform::ContextAttributes ToPlatformContextAttributes( + unsigned web_gl_version, + bool support_own_offscreen_surface) { + Platform::ContextAttributes result; ++ result.prefer_integrated_gpu = attrs.power_preference == "low-power"; + result.fail_if_major_performance_caveat = + attrs.fail_if_major_performance_caveat; + result.context_type = web_gl_version == 2 ? Platform::kWebGL2ContextType +diff --git a/third_party/blink/renderer/modules/webgl/webgl_context_attributes.idl b/third_party/blink/renderer/modules/webgl/webgl_context_attributes.idl +index 180673be9bd0..0af29cbc9402 100644 +--- a/third_party/blink/renderer/modules/webgl/webgl_context_attributes.idl ++++ b/third_party/blink/renderer/modules/webgl/webgl_context_attributes.idl +@@ -26,6 +26,12 @@ + + // https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.2 + ++enum WebGLPowerPreference { ++ "default", ++ "low-power", ++ "high-performance", ++}; ++ + dictionary WebGLContextAttributes { + boolean alpha = true; + boolean depth = true; +@@ -33,6 +33,7 @@ dictionary WebGLContextAttributes { + boolean antialias = true; + boolean premultipliedAlpha = true; + boolean preserveDrawingBuffer = false; ++ WebGLPowerPreference powerPreference = "default"; + boolean failIfMajorPerformanceCaveat = false; + [OriginTrialEnabled=WebXR] XRDevice compatibleXRDevice = null; + }; +diff --git a/third_party/blink/public/platform/platform.h b/third_party/blink/public/platform/platform.h +index d4948345246e..bc277ba6aa5f 100644 +--- a/third_party/blink/public/platform/platform.h ++++ b/third_party/blink/public/platform/platform.h +@@ -522,6 +522,7 @@ class BLINK_PLATFORM_EXPORT Platform { + kGLES3ContextType, // GLES 3.0 context + }; + struct ContextAttributes { ++ bool prefer_integrated_gpu = false; + bool fail_if_major_performance_caveat = false; + ContextType context_type = kGLES2ContextType; + // Offscreen contexts usually share a surface for the default frame buffer diff --git a/patches/common/chromium/webui_in_subframes.patch b/patches/common/chromium/webui_in_subframes.patch new file mode 100644 index 00000000000..dd4ac0fbad9 --- /dev/null +++ b/patches/common/chromium/webui_in_subframes.patch @@ -0,0 +1,138 @@ +diff --git a/content/browser/frame_host/render_frame_host_delegate.cc b/content/browser/frame_host/render_frame_host_delegate.cc +index 4d0a8ea553c5..0fac0b22ff2f 100644 +--- a/content/browser/frame_host/render_frame_host_delegate.cc ++++ b/content/browser/frame_host/render_frame_host_delegate.cc +@@ -89,8 +89,10 @@ bool RenderFrameHostDelegate::ShouldRouteMessageEvent( + } + + std::unique_ptr +-RenderFrameHostDelegate::CreateWebUIForRenderFrameHost(const GURL& url) { +- return nullptr; ++RenderFrameHostDelegate::CreateWebUIForRenderFrameHost( ++ const GURL& url, ++ const std::string& frame_name) { ++ return nullptr; + } + + bool RenderFrameHostDelegate::ShouldAllowRunningInsecureContent( +diff --git a/content/browser/frame_host/render_frame_host_delegate.h b/content/browser/frame_host/render_frame_host_delegate.h +index 197b64b49fd6..2e94b03c4f44 100644 +--- a/content/browser/frame_host/render_frame_host_delegate.h ++++ b/content/browser/frame_host/render_frame_host_delegate.h +@@ -234,7 +234,8 @@ class CONTENT_EXPORT RenderFrameHostDelegate { + // Creates a WebUI object for a frame navigating to |url|. If no WebUI + // applies, returns null. + virtual std::unique_ptr CreateWebUIForRenderFrameHost( +- const GURL& url); ++ const GURL& url, ++ const std::string& frame_name); + + // Called by |frame| to notify that it has received an update on focused + // element. |bounds_in_root_view| is the rectangle containing the element that +diff --git a/content/browser/frame_host/render_frame_host_impl.cc b/content/browser/frame_host/render_frame_host_impl.cc +index 1f566ef1f437..bb2f59d62315 100644 +--- a/content/browser/frame_host/render_frame_host_impl.cc ++++ b/content/browser/frame_host/render_frame_host_impl.cc +@@ -20,6 +20,7 @@ + #include "base/process/kill.h" + #include "base/task_scheduler/post_task.h" + #include "base/time/time.h" ++#include "base/unguessable_token.h" + #include "build/build_config.h" + #include "cc/base/switches.h" + #include "content/browser/accessibility/browser_accessibility_manager.h" +@@ -3468,8 +3514,23 @@ bool RenderFrameHostImpl::UpdatePendingWebUI(const GURL& dest_url, + DCHECK(web_ui_); + should_reuse_web_ui_ = true; + } else { ++ // Give the frame a name if it does not already have one. ++ // The reason is web ui code base the frame look up on the frame name. ++ std::string frame_name = GetFrameName(); ++ if (frame_name.empty() && !frame_tree_node_->IsMainFrame()) { ++ frame_name = base::StringPrintf("frame_%i", frame_tree_node_->frame_tree_node_id()); ++ frame_tree_node_->SetFrameName( ++ frame_name, frame_name + base::UnguessableToken::Create().ToString()); ++ } ++ ++ // If the web ui is in subframes, the parent frame bindings does not have the web ui binding, ++ // so we reset the bindings for the subframes. ++ if (!frame_tree_node_->IsMainFrame() && new_web_ui_type != WebUI::kNoWebUI) { ++ entry_bindings = NavigationEntryImpl::kInvalidBindings; ++ } ++ + // Otherwise create a new pending WebUI. +- pending_web_ui_ = delegate_->CreateWebUIForRenderFrameHost(dest_url); ++ pending_web_ui_ = delegate_->CreateWebUIForRenderFrameHost(dest_url, frame_name); + DCHECK(pending_web_ui_); + pending_web_ui_type_ = new_web_ui_type; + +diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc +index f985ea2bceab..779cfd79312d 100644 +--- a/content/browser/web_contents/web_contents_impl.cc ++++ b/content/browser/web_contents/web_contents_impl.cc +@@ -768,6 +768,25 @@ RenderFrameHostManager* WebContentsImpl::GetRenderManagerForTesting() { + return GetRenderManager(); + } + ++void SendMessageToFrameTreeWebUIs(RenderFrameHostImpl* parent_frame_host, ++ const IPC::Message& message, ++ int& dispatch_count) { ++ // Get the web ui or the pending one if it's not yet commited. ++ WebUIImpl* web_ui = parent_frame_host->web_ui() ++ ? parent_frame_host->web_ui() ++ : parent_frame_host->pending_web_ui(); ++ if (web_ui && web_ui->OnMessageReceived(message, parent_frame_host)) { ++ ++dispatch_count; ++ } ++ ++ size_t child_count = parent_frame_host->frame_tree_node()->child_count(); ++ for (size_t i = 0; i < child_count; ++i) { ++ RenderFrameHostImpl* sub_frame_host = ++ parent_frame_host->frame_tree_node()->child_at(i)->current_frame_host(); ++ SendMessageToFrameTreeWebUIs(sub_frame_host, message, dispatch_count); ++ } ++} ++ + bool WebContentsImpl::OnMessageReceived(RenderViewHostImpl* render_view_host, + const IPC::Message& message) { + for (auto& observer : observers_) { +@@ -809,9 +828,10 @@ bool WebContentsImpl::OnMessageReceived(RenderViewHostImpl* render_view_host, + + bool WebContentsImpl::OnMessageReceived(RenderFrameHostImpl* render_frame_host, + const IPC::Message& message) { +- { +- WebUIImpl* web_ui = render_frame_host->web_ui(); +- if (web_ui && web_ui->OnMessageReceived(message, render_frame_host)) ++ int dispatch_count = 0; ++ if (render_frame_host) { ++ SendMessageToFrameTreeWebUIs(render_frame_host, message, dispatch_count); ++ if (dispatch_count > 0) + return true; + } + +@@ -5021,8 +5043,9 @@ NavigationControllerImpl& WebContentsImpl::GetControllerForRenderManager() { + } + + std::unique_ptr WebContentsImpl::CreateWebUIForRenderFrameHost( +- const GURL& url) { +- return CreateWebUI(url); ++ const GURL& url, ++ const std::string& frame_name) { ++ return CreateWebUI(url/*, frame_name*/); + } + + NavigationEntry* +diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h +index 84a01a83c72a..49d0a4b547c2 100644 +--- a/content/browser/web_contents/web_contents_impl.h ++++ b/content/browser/web_contents/web_contents_impl.h +@@ -534,7 +534,8 @@ class CONTENT_EXPORT WebContentsImpl : public WebContents, + SiteInstance* source_site_instance) const override; + void EnsureOpenerProxiesExist(RenderFrameHost* source_rfh) override; + std::unique_ptr CreateWebUIForRenderFrameHost( +- const GURL& url) override; ++ const GURL& url, ++ const std::string& frame_name) override; + void SetFocusedFrame(FrameTreeNode* node, SiteInstance* source) override; + void DidCallFocus() override; + RenderFrameHost* GetFocusedFrameIncludingInnerWebContents() override; diff --git a/patches/common/chromium/webview_cross_drag.patch b/patches/common/chromium/webview_cross_drag.patch new file mode 100644 index 00000000000..d12c3f87753 --- /dev/null +++ b/patches/common/chromium/webview_cross_drag.patch @@ -0,0 +1,24 @@ +diff --git a/content/browser/web_contents/web_contents_view_aura.cc b/content/browser/web_contents/web_contents_view_aura.cc +index 1bfef2c..0ba2260 100644 +--- a/content/browser/web_contents/web_contents_view_aura.cc ++++ b/content/browser/web_contents/web_contents_view_aura.cc +@@ -675,6 +675,7 @@ gfx::NativeView WebContentsViewAura::GetRenderWidgetHostViewParent() const { + + bool WebContentsViewAura::IsValidDragTarget( + RenderWidgetHostImpl* target_rwh) const { ++ return true; + return target_rwh->GetProcess()->GetID() == drag_start_process_id_ || + GetRenderViewHostID(web_contents_->GetRenderViewHost()) != + drag_start_view_id_; +diff --git a/content/browser/web_contents/web_drag_dest_mac.mm b/content/browser/web_contents/web_drag_dest_mac.mm +index 37ed265..814a37d 100644 +--- a/content/browser/web_contents/web_drag_dest_mac.mm ++++ b/content/browser/web_contents/web_drag_dest_mac.mm +@@ -348,6 +348,7 @@ - (void)setDragStartTrackersForProcess:(int)processID { + } + + - (bool)isValidDragTarget:(content::RenderWidgetHostImpl*)targetRWH { ++ return YES; + return targetRWH->GetProcess()->GetID() == dragStartProcessID_ || + GetRenderViewHostID(webContents_->GetRenderViewHost()) != + dragStartViewID_; diff --git a/patches/common/chromium/webview_reattach.patch b/patches/common/chromium/webview_reattach.patch new file mode 100644 index 00000000000..d5f0e4dcfd6 --- /dev/null +++ b/patches/common/chromium/webview_reattach.patch @@ -0,0 +1,16 @@ +diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc +index b2d1e63..bc2cf9a 100644 +--- a/content/browser/web_contents/web_contents_impl.cc ++++ b/content/browser/web_contents/web_contents_impl.cc +@@ -4562,6 +4562,11 @@ void WebContentsImpl::NotifyViewSwapped(RenderViewHost* old_host, + for (auto& observer : observers_) + observer.RenderViewHostChanged(old_host, new_host); + ++ // If this is an inner WebContents that has swapped views, we need to reattach ++ // it to its outer WebContents. ++ if (node_.outer_web_contents()) ++ ReattachToOuterWebContentsFrame(); ++ + // Ensure that the associated embedder gets cleared after a RenderViewHost + // gets swapped, so we don't reuse the same embedder next time a + // RenderViewHost is attached to this WebContents. diff --git a/patches/common/chromium/windows_cc_wrapper.patch b/patches/common/chromium/windows_cc_wrapper.patch new file mode 100644 index 00000000000..475db682069 --- /dev/null +++ b/patches/common/chromium/windows_cc_wrapper.patch @@ -0,0 +1,45 @@ +diff --git a/build/toolchain/win/BUILD.gn b/build/toolchain/win/BUILD.gn +index a526d47e7786..946df3cd513c 100644 +--- a/build/toolchain/win/BUILD.gn ++++ b/build/toolchain/win/BUILD.gn +@@ -6,6 +6,7 @@ import("//build/config/clang/clang.gni") + import("//build/config/compiler/compiler.gni") + import("//build/config/sanitizers/sanitizers.gni") + import("//build/config/win/visual_studio_version.gni") ++import("//build/toolchain/cc_wrapper.gni") + import("//build/toolchain/clang_static_analyzer.gni") + import("//build/toolchain/goma.gni") + import("//build/toolchain/toolchain.gni") +@@ -28,8 +29,14 @@ if (use_goma) { + } else { + goma_prefix = "$goma_dir/gomacc " + } ++ clang_prefix = goma_prefix + } else { + goma_prefix = "" ++ if (cc_wrapper != "") { ++ clang_prefix = cc_wrapper + " " ++ } else { ++ clang_prefix = "" ++ } + } + + if (disable_goma) { +@@ -389,7 +396,7 @@ if (target_os == "win" && + msvc_toolchain("win_clang_" + target_cpu) { + environment = "environment." + target_cpu + prefix = rebase_path("$clang_base_path/bin", root_build_dir) +- cl = "${goma_prefix}$prefix/${clang_cl}" ++ cl = "${clang_prefix}$prefix/${clang_cl}" + sys_include_flags = "${target_cpu_toolchain_data.include_flags_imsvc}" + + toolchain_args = { +@@ -431,7 +438,7 @@ template("win_x64_toolchains") { + msvc_toolchain("win_clang_" + target_name) { + environment = "environment.x64" + prefix = rebase_path("$clang_base_path/bin", root_build_dir) +- cl = "${goma_prefix}$prefix/${clang_cl}" ++ cl = "${clang_prefix}$prefix/${clang_cl}" + sys_include_flags = "${x64_toolchain_data.include_flags_imsvc}" + + toolchain_args = { diff --git a/patches/common/chromium/worker_context_will_destroy.patch b/patches/common/chromium/worker_context_will_destroy.patch new file mode 100644 index 00000000000..c83f39293ff --- /dev/null +++ b/patches/common/chromium/worker_context_will_destroy.patch @@ -0,0 +1,74 @@ +diff --git a/content/public/renderer/content_renderer_client.h b/content/public/renderer/content_renderer_client.h +index 0e554ba8467a..8e56489a5152 100644 +--- a/content/public/renderer/content_renderer_client.h ++++ b/content/public/renderer/content_renderer_client.h +@@ -351,6 +351,11 @@ class CONTENT_EXPORT ContentRendererClient { + virtual void DidInitializeWorkerContextOnWorkerThread( + v8::Local context) {} + ++ // Notifies that a worker context will be destroyed. This function is called ++ // from the worker thread. ++ virtual void WillDestroyWorkerContextOnWorkerThread( ++ v8::Local context) {} ++ + // Overwrites the given URL to use an HTML5 embed if possible. + // An empty URL is returned if the URL is not overriden. + virtual GURL OverrideFlashEmbedWithHTML(const GURL& url); +diff --git a/content/renderer/renderer_blink_platform_impl.cc b/content/renderer/renderer_blink_platform_impl.cc +index 0affacaa0294..eca456faa640 100644 +--- a/content/renderer/renderer_blink_platform_impl.cc ++++ b/content/renderer/renderer_blink_platform_impl.cc +@@ -1402,6 +1404,12 @@ void RendererBlinkPlatformImpl::WillStopWorkerThread() { + WorkerThreadRegistry::Instance()->WillStopCurrentWorkerThread(); + } + ++void RendererBlinkPlatformImpl::WorkerContextWillDestroy( ++ const v8::Local& worker) { ++ GetContentClient()->renderer()->WillDestroyWorkerContextOnWorkerThread( ++ worker); ++} ++ + void RendererBlinkPlatformImpl::WorkerContextCreated( + const v8::Local& worker) { + GetContentClient()->renderer()->DidInitializeWorkerContextOnWorkerThread( +diff --git a/content/renderer/renderer_blink_platform_impl.h b/content/renderer/renderer_blink_platform_impl.h +index e8a4578009d1..e9ba4e7f391f 100644 +--- a/content/renderer/renderer_blink_platform_impl.h ++++ b/content/renderer/renderer_blink_platform_impl.h +@@ -219,6 +219,7 @@ class CONTENT_EXPORT RendererBlinkPlatformImpl : public BlinkPlatformImpl { + void DidStartWorkerThread() override; + void WillStopWorkerThread() override; + void WorkerContextCreated(const v8::Local& worker) override; ++ void WorkerContextWillDestroy(const v8::Local& worker) override; + + // Set the PlatformEventObserverBase in |platform_event_observers_| associated + // with |type| to |observer|. If there was already an observer associated to +diff --git a/third_party/blink/renderer/core/workers/worker_thread.cc b/third_party/blink/renderer/core/workers/worker_thread.cc +index a522ba4dbdf7..6991078b36f5 100644 +--- a/third_party/blink/renderer/core/workers/worker_thread.cc ++++ b/third_party/blink/renderer/core/workers/worker_thread.cc +@@ -481,6 +481,12 @@ void WorkerThread::PrepareForShutdownOnWorkerThread() { + SetExitCode(ExitCode::kGracefullyTerminated); + } + ++ { ++ v8::HandleScope handle_scope(GetIsolate()); ++ Platform::Current()->WorkerContextWillDestroy( ++ GlobalScope()->ScriptController()->GetContext()); ++ } ++ + inspector_task_runner_->Dispose(); + GetWorkerReportingProxy().WillDestroyWorkerGlobalScope(); + probe::AllAsyncTasksCanceled(GlobalScope()); +diff --git a/third_party/blink/public/platform/platform.h b/third_party/blink/public/platform/platform.h +index 98ecb84..0779d4a 100644 +--- a/third_party/blink/public/platform/platform.h ++++ b/third_party/blink/public/platform/platform.h +@@ -596,6 +596,7 @@ class BLINK_PLATFORM_EXPORT Platform { + virtual void DidStartWorkerThread() {} + virtual void WillStopWorkerThread() {} + virtual void WorkerContextCreated(const v8::Local& worker) {} ++ virtual void WorkerContextWillDestroy(const v8::Local& worker) {} + virtual bool AllowScriptExtensionForServiceWorker(const WebURL& script_url) { + return false; + } diff --git a/patches/common/crashpad/.patches.yaml b/patches/common/crashpad/.patches.yaml new file mode 100644 index 00000000000..102c63372fe --- /dev/null +++ b/patches/common/crashpad/.patches.yaml @@ -0,0 +1,8 @@ +repo: src +patches: +- + author: Jeremy Apthorp + file: http_status.patch + description: | + Accept all HTTP codes in [200, 300) as successful, instead of just 200. + For example HockeyApp responds with 202. diff --git a/patches/common/crashpad/http_status.patch b/patches/common/crashpad/http_status.patch new file mode 100644 index 00000000000..4930b4de48d --- /dev/null +++ b/patches/common/crashpad/http_status.patch @@ -0,0 +1,54 @@ +From 800aa10d300af0f3fe162ae586b6b1ebe0566ab4 Mon Sep 17 00:00:00 2001 +From: Catalin Fratila +Date: Fri, 19 May 2017 09:28:53 +0200 +Subject: [PATCH] Handle everything not in [200, 300) as error. For example + HockeyApp responds with 202. + +(cherry picked from commit f7c320766756a8aaa45ccbcff2945053d9f7e109) +(cherry picked from commit 1875fddc7e671b14d8b54068301d9648d12e9dc2) +(cherry picked from commit 670fb453b0c3d6ae0a0d5923f68df02464337617) +--- + third_party/crashpad/crashpad/util/net/http_transport_libcurl.cc | 2 +- + third_party/crashpad/crashpad/util/net/http_transport_mac.mm | 2 +- + third_party/crashpad/crashpad/util/net/http_transport_win.cc | 2 +- + 3 files changed, 3 insertions(+), 3 deletions(-) + +diff --git a/third_party/crashpad/crashpad/util/net/http_transport_libcurl.cc b/third_party/crashpad/crashpad/util/net/http_transport_libcurl.cc +index c16a593..0e262b0 100644 +--- a/third_party/crashpad/crashpad/util/net/http_transport_libcurl.cc ++++ b/third_party/crashpad/crashpad/util/net/http_transport_libcurl.cc +@@ -338,7 +338,7 @@ bool HTTPTransportLibcurl::ExecuteSynchronously(std::string* response_body) { + return false; + } + +- if (status != 200) { ++ if (status < 200 || status >= 300) { + LOG(ERROR) << base::StringPrintf("HTTP status %ld", status); + return false; + } +diff --git a/third_party/crashpad/crashpad/util/net/http_transport_mac.mm b/third_party/crashpad/crashpad/util/net/http_transport_mac.mm +index 8d5f78c..a6434c2 100644 +--- a/third_party/crashpad/crashpad/util/net/http_transport_mac.mm ++++ b/third_party/crashpad/crashpad/util/net/http_transport_mac.mm +@@ -293,7 +293,7 @@ static void Unschedule(CFReadStreamRef stream, + return false; + } + NSInteger http_status = [http_response statusCode]; +- if (http_status != 200) { ++ if (http_status < 200 || http_status >= 300) { + LOG(ERROR) << base::StringPrintf("HTTP status %ld", + implicit_cast(http_status)); + return false; +diff --git a/third_party/crashpad/crashpad/util/net/http_transport_win.cc b/third_party/crashpad/crashpad/util/net/http_transport_win.cc +index 18d343c..40c3061 100644 +--- a/third_party/crashpad/crashpad/util/net/http_transport_win.cc ++++ b/third_party/crashpad/crashpad/util/net/http_transport_win.cc +@@ -375,7 +375,7 @@ bool HTTPTransportWin::ExecuteSynchronously(std::string* response_body) { + return false; + } + +- if (status_code != 200) { ++ if (status_code < 200 || status_code >= 300) { + LOG(ERROR) << base::StringPrintf("HTTP status %lu", status_code); + return false; + } diff --git a/patches/common/ffmpeg/.patches.yaml b/patches/common/ffmpeg/.patches.yaml new file mode 100644 index 00000000000..38e2a5a8065 --- /dev/null +++ b/patches/common/ffmpeg/.patches.yaml @@ -0,0 +1,15 @@ +repo: src/third_party/ffmpeg +patches: +- + author: Ales Pergl + file: build_gn.patch + description: | + Chromium's Mac toolchain sets the "install_name" linker parameter only + when "is_component_build" is true, but we want to set even if it's false, + because we are making a dylib which will be distributed inside a bundle. +- + author: Aleksei Kuzmin + file: fix_build_on_linux_x86.patch + description: | + Builds on Linux x86 fail with a clang error. See https://crbug.com/796379. + Once it's fixed the patch can be removed. diff --git a/patches/common/ffmpeg/build_gn.patch b/patches/common/ffmpeg/build_gn.patch new file mode 100644 index 00000000000..b67cff2ad61 --- /dev/null +++ b/patches/common/ffmpeg/build_gn.patch @@ -0,0 +1,15 @@ +diff --git a/BUILD.gn b/BUILD.gn +index 5439b39693..6783292c3b 100755 +--- a/BUILD.gn ++++ b/BUILD.gn +@@ -393,6 +393,10 @@ if (is_component_ffmpeg) { + # So we can append below and assume they're defined. + ldflags = [] + ++ if (!is_component_build && is_mac) { ++ ldflags += [ "-Wl,-install_name,@rpath/libffmpeg.dylib" ] ++ } ++ + if (is_fuchsia || (is_posix && !is_mac)) { + # Fixes warnings PIC relocation when building as component. + ldflags += [ diff --git a/patches/common/ffmpeg/fix_build_on_linux_x86.patch b/patches/common/ffmpeg/fix_build_on_linux_x86.patch new file mode 100644 index 00000000000..52d5f756815 --- /dev/null +++ b/patches/common/ffmpeg/fix_build_on_linux_x86.patch @@ -0,0 +1,13 @@ +diff --git a/BUILD.gn b/BUILD.gn +index ff09111634..fa7712a3a3 100755 +--- a/BUILD.gn ++++ b/BUILD.gn +@@ -247,7 +247,7 @@ target(link_target_type, "ffmpeg_internal") { + # On POSIX x86, sanitizers will fail to compiler the H264 CABAC code due to + # insufficient registers unless we disable EBP usage. crbug.com/786760 + if (target_cpu == "x86") { +- if (using_sanitizer) { ++ if (using_sanitizer || is_electron_build) { + defines += [ "HAVE_EBP_AVAILABLE=0" ] + } else { + defines += [ "HAVE_EBP_AVAILABLE=1" ] diff --git a/patches/common/icu/.patches.yaml b/patches/common/icu/.patches.yaml new file mode 100644 index 00000000000..3f44396b391 --- /dev/null +++ b/patches/common/icu/.patches.yaml @@ -0,0 +1,10 @@ +repo: src/third_party/icu +patches: +- + author: Ales Pergl + file: build_gn.patch + description: null +- + author: Cheng Zhao + file: no_inline_default_constructor.patch + description: null diff --git a/patches/common/icu/build_gn.patch b/patches/common/icu/build_gn.patch new file mode 100644 index 00000000000..f9d9b74595a --- /dev/null +++ b/patches/common/icu/build_gn.patch @@ -0,0 +1,63 @@ +diff --git a/BUILD.gn b/BUILD.gn +index 76914cd7..a44d7896 100644 +--- a/BUILD.gn ++++ b/BUILD.gn +@@ -34,7 +34,7 @@ config("icu_config") { + "U_ENABLE_DYLOAD=0", + ] + +- if (!is_component_build) { ++ if (!is_component_build && !(is_electron_build && !is_electron_gn_build)) { + defines += [ "U_STATIC_IMPLEMENTATION" ] + } + +@@ -537,6 +537,24 @@ component("icui18n") { + ":icuuc", + ] + ++ # In Electron all of ICU is in one binary, hence we must build with ++ # U_COMBINED_IMPLEMENTATION defined. ++ # Also, for the "static_library" configuration, keep icui18n as ++ # a shared library so that other Chromium targets build cleanly. ++ if (is_electron_build && !is_electron_gn_build) { ++ defines += [ "U_COMBINED_IMPLEMENTATION" ] ++ ++ if (!is_component_build) { ++ static_component_type = "shared_library" ++ ++ # Because GN already applied the wrong defaults (see the ++ # set_defaults("component") statement in BUILDCONFIG.gn) we must reset ++ # the configs and assign those for shared libraries. ++ configs = [] ++ configs = default_shared_library_configs ++ } ++ } ++ + # ICU uses RTTI, replace the default "no rtti" config. + configs -= [ + "//build/config/compiler:no_rtti", # ICU uses RTTI. +@@ -945,6 +963,24 @@ component("icuuc") { + ":icudata", + ] + ++ # In Electron all of ICU is in one binary, hence we must build with ++ # U_COMBINED_IMPLEMENTATION defined. ++ # Also, for the "static_library" configuration, keep icuuc as ++ # a shared library so that other Chromium targets build cleanly. ++ if (is_electron_build && !is_electron_gn_build) { ++ defines += [ "U_COMBINED_IMPLEMENTATION" ] ++ ++ if (!is_component_build) { ++ static_component_type = "shared_library" ++ ++ # Because GN already applied the wrong defaults (see the ++ # set_defaults("component") statement in BUILDCONFIG.gn) we must reset ++ # the configs and assign those for shared libraries. ++ configs = [] ++ configs = default_shared_library_configs ++ } ++ } ++ + configs -= [ + "//build/config/compiler:no_rtti", # ICU uses RTTI. + "//build/config/compiler:chromium_code", diff --git a/patches/common/icu/no_inline_default_constructor.patch b/patches/common/icu/no_inline_default_constructor.patch new file mode 100644 index 00000000000..a5ef18446ea --- /dev/null +++ b/patches/common/icu/no_inline_default_constructor.patch @@ -0,0 +1,44 @@ +diff --git a/source/common/unicode/unistr.h b/source/common/unicode/unistr.h +index e0ab0b9e..fe4c673b 100644 +--- a/source/common/unicode/unistr.h ++++ b/source/common/unicode/unistr.h +@@ -2957,7 +2957,7 @@ public: + /** Construct an empty UnicodeString. + * @stable ICU 2.0 + */ +- inline UnicodeString(); ++ UnicodeString(); + + /** + * Construct a UnicodeString with capacity to hold capacity char16_ts +@@ -3915,15 +3915,6 @@ UnicodeString::getArrayStart() const { + fUnion.fStackFields.fBuffer : fUnion.fFields.fArray; + } + +-//======================================== +-// Default constructor +-//======================================== +- +-inline +-UnicodeString::UnicodeString() { +- fUnion.fStackFields.fLengthAndFlags=kShortString; +-} +- + inline UnicodeString::UnicodeString(const std::nullptr_t /*text*/) { + fUnion.fStackFields.fLengthAndFlags=kShortString; + } +diff --git a/source/common/unistr.cpp b/source/common/unistr.cpp +index 1bfb71aa..5495ee91 100644 +--- a/source/common/unistr.cpp ++++ b/source/common/unistr.cpp +@@ -146,7 +146,9 @@ UnicodeString::releaseArray() { + // Constructors + //======================================== + +-// The default constructor is inline in unistr.h. ++UnicodeString::UnicodeString() { ++ fUnion.fStackFields.fLengthAndFlags=kShortString; ++} + + UnicodeString::UnicodeString(int32_t capacity, UChar32 c, int32_t count) { + fUnion.fFields.fLengthAndFlags = 0; diff --git a/patches/common/skia/.patches.yaml b/patches/common/skia/.patches.yaml new file mode 100644 index 00000000000..5d634838cef --- /dev/null +++ b/patches/common/skia/.patches.yaml @@ -0,0 +1,6 @@ +repo: src/third_party/skia +patches: +- + author: Ales Pergl + file: dcheck.patch + description: null diff --git a/patches/common/skia/dcheck.patch b/patches/common/skia/dcheck.patch new file mode 100644 index 00000000000..604304295cd --- /dev/null +++ b/patches/common/skia/dcheck.patch @@ -0,0 +1,13 @@ +diff --git a/include/core/SkPostConfig.h b/include/core/SkPostConfig.h +index c34397cde6..5a55535eeb 100644 +--- a/include/core/SkPostConfig.h ++++ b/include/core/SkPostConfig.h +@@ -18,7 +18,7 @@ + #ifdef NDEBUG + #define SK_RELEASE + #else +- #define SK_DEBUG ++ #define SK_RELEASE + #endif + #endif + diff --git a/patches/common/v8/.patches.yaml b/patches/common/v8/.patches.yaml new file mode 100644 index 00000000000..96410ed23f3 --- /dev/null +++ b/patches/common/v8/.patches.yaml @@ -0,0 +1,87 @@ +repo: src/v8 +patches: +- + author: Shelley Vohr + file: add_realloc.patch + description: | + Blink overrides ArrayBuffer's allocator with its own one, while Node simply + uses malloc and free, so we need to use v8's allocator in Node. As part of the + 10.6.0 upgrade, we needed to make SerializerDelegate accept an allocator + argument in its constructor, and override ReallocateBufferMemory and + FreeBufferMemory to use the allocator. We cannot simply allocate and then memcpy + when we override ReallocateBufferMemory, so we therefore need to implement + Realloc on the v8 side. +- + author: Ales Pergl + file: build_gn.patch + description: null +- + author: Cheng Zhao + file: array_buffer.patch + description: null +- + author: Cheng Zhao + file: ostreams.patch + description: null +- + author: Aleksei Kuzmin + file: export_platform.patch + description: | + v8::Platform::SystemClockTimeMillis must be exported so that node::NodePlatform can call it +- + author: Ales Pergl + file: dcheck.patch + description: null +- + author: Nitish Sakhawalkar + file: disable-warning-win.patch + description: + Disable unit test windows build warning +- + author: Aleksei Kuzmin + file: backport_39d546a.patch + description: Node 10.0.0 needs it. +- + author: Aleksei Kuzmin + file: backport_ff0a97933.patch + description: Node 10.2.0 needs it. +- + author: Aleksei Kuzmin + file: backport_9fb02b526.patch + description: Node 10.2.0 needs it. +- + author: Aleksei Kuzmin + file: backport_23652c5f.patch + description: Node 10.2.0 needs it. +- + author: Shelley Vohr + file: backport_91ddb65d.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: cherry-pick_6989b3f6d7.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: cherry-pick_a440efb27f.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: cherry-pick_5dd3395.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: backport_aa6ce3e.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: cherry-pick_b20faff.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: cherry-pick_acc336c.patch + description: Node 10.6.0 needs it. +- + author: Shelley Vohr + file: cherry-pick_70c4340.patch + description: Node 10.6.0 needs it. diff --git a/patches/common/v8/add_realloc.patch b/patches/common/v8/add_realloc.patch new file mode 100644 index 00000000000..4480357af33 --- /dev/null +++ b/patches/common/v8/add_realloc.patch @@ -0,0 +1,33 @@ +diff --git a/include/v8.h b/include/v8.h +index 573e80176d..5eefe26fe9 100644 +--- a/include/v8.h ++++ b/include/v8.h +@@ -4318,6 +4318,13 @@ class V8_EXPORT ArrayBuffer : public Object { + */ + virtual void* AllocateUninitialized(size_t length) = 0; + ++ /** ++ * Free the memory block of size |length|, pointed to by |data|. ++ * That memory must be previously allocated by |Allocate| and not yet freed ++ * with a call to |Free| or |Realloc| ++ */ ++ virtual void* Realloc(void* data, size_t length); ++ + /** + * Free the memory block of size |length|, pointed to by |data|. + * That memory is guaranteed to be previously allocated by |Allocate|. +diff --git a/src/api.cc b/src/api.cc +index 8b177d041d..e06ca2a207 100644 +--- a/src/api.cc ++++ b/src/api.cc +@@ -460,6 +460,10 @@ void V8::SetSnapshotDataBlob(StartupData* snapshot_blob) { + i::V8::SetSnapshotBlob(snapshot_blob); + } + ++void* v8::ArrayBuffer::Allocator::Realloc(void* data, size_t length) { ++ UNIMPLEMENTED(); ++} ++ + namespace { + + class ArrayBufferAllocator : public v8::ArrayBuffer::Allocator { diff --git a/patches/common/v8/array_buffer.patch b/patches/common/v8/array_buffer.patch new file mode 100644 index 00000000000..28d3c9488c6 --- /dev/null +++ b/patches/common/v8/array_buffer.patch @@ -0,0 +1,32 @@ +diff --git a/include/v8.h b/include/v8.h +index 573e80176d..80bfd1d22a 100644 +--- a/include/v8.h ++++ b/include/v8.h +@@ -7337,6 +7337,9 @@ class V8_EXPORT Isolate { + */ + void SetIdle(bool is_idle); + ++ /** Returns the ArrayBuffer::Allocator used in this isolate. */ ++ ArrayBuffer::Allocator* GetArrayBufferAllocator(); ++ + /** Returns true if this isolate has a current context. */ + bool InContext(); + +diff --git a/src/api.cc b/src/api.cc +index 8b177d041d..f58a350f0f 100644 +--- a/src/api.cc ++++ b/src/api.cc +@@ -8139,6 +8139,13 @@ void Isolate::SetIdle(bool is_idle) { + isolate->SetIdle(is_idle); + } + ++ ++ArrayBuffer::Allocator* Isolate::GetArrayBufferAllocator() { ++ i::Isolate* isolate = reinterpret_cast(this); ++ return isolate->array_buffer_allocator(); ++} ++ ++ + bool Isolate::InContext() { + i::Isolate* isolate = reinterpret_cast(this); + return isolate->context() != nullptr; diff --git a/patches/common/v8/backport_23652c5f.patch b/patches/common/v8/backport_23652c5f.patch new file mode 100644 index 00000000000..6aee5c1b2f3 --- /dev/null +++ b/patches/common/v8/backport_23652c5f.patch @@ -0,0 +1,161 @@ +23652c5f4cd07dd6304f78b407541c6a02caf60e +diff --git a/include/libplatform/v8-tracing.h b/include/libplatform/v8-tracing.h +index 9dcf3d7bca..e430e7c350 100644 +--- a/include/libplatform/v8-tracing.h ++++ b/include/libplatform/v8-tracing.h +@@ -112,6 +112,8 @@ class V8_PLATFORM_EXPORT TraceWriter { + virtual void Flush() = 0; + + static TraceWriter* CreateJSONTraceWriter(std::ostream& stream); ++ static TraceWriter* CreateJSONTraceWriter(std::ostream& stream, ++ const std::string& tag); + + private: + // Disallow copy and assign +diff --git a/src/libplatform/tracing/trace-writer.cc b/src/libplatform/tracing/trace-writer.cc +index 36a8783499..7bfc766469 100644 +--- a/src/libplatform/tracing/trace-writer.cc ++++ b/src/libplatform/tracing/trace-writer.cc +@@ -119,8 +119,12 @@ void JSONTraceWriter::AppendArgValue(ConvertableToTraceFormat* value) { + stream_ << arg_stringified; + } + +-JSONTraceWriter::JSONTraceWriter(std::ostream& stream) : stream_(stream) { +- stream_ << "{\"traceEvents\":["; ++JSONTraceWriter::JSONTraceWriter(std::ostream& stream) ++ : JSONTraceWriter(stream, "traceEvents") {} ++ ++JSONTraceWriter::JSONTraceWriter(std::ostream& stream, const std::string& tag) ++ : stream_(stream) { ++ stream_ << "{\"" << tag << "\":["; + } + + JSONTraceWriter::~JSONTraceWriter() { stream_ << "]}"; } +@@ -171,6 +175,11 @@ TraceWriter* TraceWriter::CreateJSONTraceWriter(std::ostream& stream) { + return new JSONTraceWriter(stream); + } + ++TraceWriter* TraceWriter::CreateJSONTraceWriter(std::ostream& stream, ++ const std::string& tag) { ++ return new JSONTraceWriter(stream, tag); ++} ++ + } // namespace tracing + } // namespace platform + } // namespace v8 +diff --git a/src/libplatform/tracing/trace-writer.h b/src/libplatform/tracing/trace-writer.h +index 7e1bdc24d6..d811351389 100644 +--- a/src/libplatform/tracing/trace-writer.h ++++ b/src/libplatform/tracing/trace-writer.h +@@ -14,6 +14,7 @@ namespace tracing { + class JSONTraceWriter : public TraceWriter { + public: + explicit JSONTraceWriter(std::ostream& stream); ++ JSONTraceWriter(std::ostream& stream, const std::string& tag); + ~JSONTraceWriter(); + void AppendTraceEvent(TraceObject* trace_event) override; + void Flush() override; +diff --git a/test/cctest/libplatform/test-tracing.cc b/test/cctest/libplatform/test-tracing.cc +index da202057de..b949785bcf 100644 +--- a/test/cctest/libplatform/test-tracing.cc ++++ b/test/cctest/libplatform/test-tracing.cc +@@ -128,44 +128,42 @@ TEST(TestTraceBufferRingBuffer) { + delete ring_buffer; + } + +-TEST(TestJSONTraceWriter) { +- std::ostringstream stream; +- // Create a scope for the tracing controller to terminate the trace writer. +- { +- v8::Platform* old_platform = i::V8::GetCurrentPlatform(); +- std::unique_ptr default_platform( +- v8::platform::NewDefaultPlatform()); +- i::V8::SetPlatformForTesting(default_platform.get()); +- auto tracing = +- base::make_unique(); +- v8::platform::tracing::TracingController* tracing_controller = +- tracing.get(); +- static_cast(default_platform.get()) +- ->SetTracingController(std::move(tracing)); +- TraceWriter* writer = TraceWriter::CreateJSONTraceWriter(stream); ++void PopulateJSONWriter(TraceWriter* writer) { ++ v8::Platform* old_platform = i::V8::GetCurrentPlatform(); ++ std::unique_ptr default_platform( ++ v8::platform::NewDefaultPlatform()); ++ i::V8::SetPlatformForTesting(default_platform.get()); ++ auto tracing = base::make_unique(); ++ v8::platform::tracing::TracingController* tracing_controller = tracing.get(); ++ static_cast(default_platform.get()) ++ ->SetTracingController(std::move(tracing)); + +- TraceBuffer* ring_buffer = +- TraceBuffer::CreateTraceBufferRingBuffer(1, writer); +- tracing_controller->Initialize(ring_buffer); +- TraceConfig* trace_config = new TraceConfig(); +- trace_config->AddIncludedCategory("v8-cat"); +- tracing_controller->StartTracing(trace_config); ++ TraceBuffer* ring_buffer = ++ TraceBuffer::CreateTraceBufferRingBuffer(1, writer); ++ tracing_controller->Initialize(ring_buffer); ++ TraceConfig* trace_config = new TraceConfig(); ++ trace_config->AddIncludedCategory("v8-cat"); ++ tracing_controller->StartTracing(trace_config); + +- TraceObject trace_object; +- trace_object.InitializeForTesting( +- 'X', tracing_controller->GetCategoryGroupEnabled("v8-cat"), "Test0", +- v8::internal::tracing::kGlobalScope, 42, 123, 0, nullptr, nullptr, +- nullptr, nullptr, TRACE_EVENT_FLAG_HAS_ID, 11, 22, 100, 50, 33, 44); +- writer->AppendTraceEvent(&trace_object); +- trace_object.InitializeForTesting( +- 'Y', tracing_controller->GetCategoryGroupEnabled("v8-cat"), "Test1", +- v8::internal::tracing::kGlobalScope, 43, 456, 0, nullptr, nullptr, +- nullptr, nullptr, 0, 55, 66, 110, 55, 77, 88); +- writer->AppendTraceEvent(&trace_object); +- tracing_controller->StopTracing(); +- i::V8::SetPlatformForTesting(old_platform); +- } ++ TraceObject trace_object; ++ trace_object.InitializeForTesting( ++ 'X', tracing_controller->GetCategoryGroupEnabled("v8-cat"), "Test0", ++ v8::internal::tracing::kGlobalScope, 42, 123, 0, nullptr, nullptr, ++ nullptr, nullptr, TRACE_EVENT_FLAG_HAS_ID, 11, 22, 100, 50, 33, 44); ++ writer->AppendTraceEvent(&trace_object); ++ trace_object.InitializeForTesting( ++ 'Y', tracing_controller->GetCategoryGroupEnabled("v8-cat"), "Test1", ++ v8::internal::tracing::kGlobalScope, 43, 456, 0, nullptr, nullptr, ++ nullptr, nullptr, 0, 55, 66, 110, 55, 77, 88); ++ writer->AppendTraceEvent(&trace_object); ++ tracing_controller->StopTracing(); ++ i::V8::SetPlatformForTesting(old_platform); ++} + ++TEST(TestJSONTraceWriter) { ++ std::ostringstream stream; ++ TraceWriter* writer = TraceWriter::CreateJSONTraceWriter(stream); ++ PopulateJSONWriter(writer); + std::string trace_str = stream.str(); + std::string expected_trace_str = + "{\"traceEvents\":[{\"pid\":11,\"tid\":22,\"ts\":100,\"tts\":50," +@@ -177,6 +175,21 @@ TEST(TestJSONTraceWriter) { + CHECK_EQ(expected_trace_str, trace_str); + } + ++TEST(TestJSONTraceWriterWithCustomtag) { ++ std::ostringstream stream; ++ TraceWriter* writer = TraceWriter::CreateJSONTraceWriter(stream, "customTag"); ++ PopulateJSONWriter(writer); ++ std::string trace_str = stream.str(); ++ std::string expected_trace_str = ++ "{\"customTag\":[{\"pid\":11,\"tid\":22,\"ts\":100,\"tts\":50," ++ "\"ph\":\"X\",\"cat\":\"v8-cat\",\"name\":\"Test0\",\"dur\":33," ++ "\"tdur\":44,\"id\":\"0x2a\",\"args\":{}},{\"pid\":55,\"tid\":66," ++ "\"ts\":110,\"tts\":55,\"ph\":\"Y\",\"cat\":\"v8-cat\",\"name\":" ++ "\"Test1\",\"dur\":77,\"tdur\":88,\"args\":{}}]}"; ++ ++ CHECK_EQ(expected_trace_str, trace_str); ++} ++ + TEST(TestTracingController) { + v8::Platform* old_platform = i::V8::GetCurrentPlatform(); + std::unique_ptr default_platform( diff --git a/patches/common/v8/backport_2eb23a17.patch b/patches/common/v8/backport_2eb23a17.patch new file mode 100644 index 00000000000..7192ae7a701 --- /dev/null +++ b/patches/common/v8/backport_2eb23a17.patch @@ -0,0 +1,1008 @@ +From 29409d7906f3e434562c492493e7299a64ac0608 Mon Sep 17 00:00:00 2001 +From: Sigurd Schneider +Date: Thu, 26 Apr 2018 18:54:18 +0200 +Subject: [PATCH] Version 6.7.288.19 (cherry-pick) + +Merged a2126f027128df6144d83db09cd841799c6b73dd + +Reland "[builtins] Separate species protectors for Array, TypedArray, Promise" + +TBR=bmeurer@chromium.org, hablich@chromium.org + +Bug: chromium:835347 +Cq-Include-Trybots: luci.chromium.try:linux_chromium_rel_ng +Change-Id: Id2ff04fb9e923ae6532d8800c2d9c770cfd945a9 +Reviewed-on: https://chromium-review.googlesource.com/1030553 +Reviewed-by: Sigurd Schneider +Cr-Commit-Position: refs/branch-heads/6.7@{#36} +Cr-Branched-From: 8457e810efd34381448d51d93f50079cf1f6a812-refs/heads/6.7.288@{#2} +Cr-Branched-From: e921be5c4f2c6407936bde750992dedbf47c1016-refs/heads/master@{#52547} +(cherry picked from commit 2eb23a17cc9af7fb9c7a64d0c9c794772642d77d) +--- + src/builtins/builtins-array-gen.cc | 6 +- + src/builtins/builtins-array.cc | 4 +- + src/builtins/builtins-promise-gen.cc | 4 +- + src/builtins/builtins-typedarray-gen.cc | 2 +- + src/code-stub-assembler.cc | 20 ++++- + src/code-stub-assembler.h | 94 ++++++++++++---------- + src/compiler/js-call-reducer.cc | 24 +++--- + src/heap/heap.h | 8 +- + src/heap/setup-heap-internal.cc | 10 ++- + src/isolate-inl.h | 16 +++- + src/isolate.cc | 27 +++++-- + src/isolate.h | 8 +- + src/lookup.cc | 64 ++++++++++----- + src/objects.cc | 2 +- + src/runtime/runtime-array.cc | 2 +- + src/runtime/runtime-test.cc | 17 +++- + src/runtime/runtime.h | 4 +- + test/cctest/test-typedarrays.cc | 6 +- + .../es6/array-species-constructor-accessor.js | 2 +- + .../es6/array-species-constructor-delete.js | 2 +- + test/mjsunit/es6/array-species-constructor.js | 2 +- + test/mjsunit/es6/array-species-delete.js | 2 +- + test/mjsunit/es6/array-species-modified.js | 2 +- + .../es6/array-species-parent-constructor.js | 2 +- + test/mjsunit/es6/array-species-proto.js | 2 +- + test/mjsunit/harmony/regexp-named-captures.js | 22 ++--- + test/mjsunit/keyed-store-generic.js | 4 +- + tools/v8heapconst.py | 57 ++++++------- + 28 files changed, 263 insertions(+), 152 deletions(-) + +diff --git a/src/builtins/builtins-array-gen.cc b/src/builtins/builtins-array-gen.cc +index 52a6222882..e44f6cddcc 100644 +--- a/src/builtins/builtins-array-gen.cc ++++ b/src/builtins/builtins-array-gen.cc +@@ -807,7 +807,7 @@ Node* ArrayBuiltinsAssembler::FindProcessor(Node* k_value, Node* k) { + GotoIfNot(IsPrototypeInitialArrayPrototype(context(), original_map), + &runtime); + +- Node* species_protector = SpeciesProtectorConstant(); ++ Node* species_protector = ArraySpeciesProtectorConstant(); + Node* value = + LoadObjectField(species_protector, PropertyCell::kValueOffset); + TNode const protector_invalid = +@@ -853,7 +853,7 @@ Node* ArrayBuiltinsAssembler::FindProcessor(Node* k_value, Node* k) { + GotoIfNot(IsPrototypeInitialArrayPrototype(context(), original_map), + &runtime); + +- Node* species_protector = SpeciesProtectorConstant(); ++ Node* species_protector = ArraySpeciesProtectorConstant(); + Node* value = + LoadObjectField(species_protector, PropertyCell::kValueOffset); + Node* const protector_invalid = SmiConstant(Isolate::kProtectorInvalid); +@@ -1146,7 +1146,7 @@ class ArrayPrototypeSliceCodeStubAssembler : public CodeStubAssembler { + + GotoIf(IsNoElementsProtectorCellInvalid(), slow); + +- GotoIf(IsSpeciesProtectorCellInvalid(), slow); ++ GotoIf(IsArraySpeciesProtectorCellInvalid(), slow); + + // Bailout if receiver has slow elements. + Node* elements_kind = LoadMapElementsKind(map); +diff --git a/src/builtins/builtins-array.cc b/src/builtins/builtins-array.cc +index 7e3f948cbe..15a77e5eae 100644 +--- a/src/builtins/builtins-array.cc ++++ b/src/builtins/builtins-array.cc +@@ -248,7 +248,7 @@ BUILTIN(ArraySplice) { + // If this is a subclass of Array, then call out to JS. + !Handle::cast(receiver)->HasArrayPrototype(isolate) || + // If anything with @@species has been messed with, call out to JS. +- !isolate->IsSpeciesLookupChainIntact())) { ++ !isolate->IsArraySpeciesLookupChainIntact())) { + return CallJsIntrinsic(isolate, isolate->array_splice(), args); + } + Handle array = Handle::cast(receiver); +@@ -1118,7 +1118,7 @@ BUILTIN(ArrayConcat) { + // Avoid a real species read to avoid extra lookups to the array constructor + if (V8_LIKELY(receiver->IsJSArray() && + Handle::cast(receiver)->HasArrayPrototype(isolate) && +- isolate->IsSpeciesLookupChainIntact())) { ++ isolate->IsArraySpeciesLookupChainIntact())) { + if (Fast_ArrayConcat(isolate, &args).ToHandle(&result_array)) { + return *result_array; + } +diff --git a/src/builtins/builtins-promise-gen.cc b/src/builtins/builtins-promise-gen.cc +index 032d0ef100..4d61f3eada 100644 +--- a/src/builtins/builtins-promise-gen.cc ++++ b/src/builtins/builtins-promise-gen.cc +@@ -536,7 +536,7 @@ void PromiseBuiltinsAssembler::BranchIfPromiseSpeciesLookupChainIntact( + GotoIfForceSlowPath(if_slow); + GotoIfNot(WordEqual(LoadMapPrototype(promise_map), promise_prototype), + if_slow); +- Branch(IsSpeciesProtectorCellInvalid(), if_slow, if_fast); ++ Branch(IsPromiseSpeciesProtectorCellInvalid(), if_slow, if_fast); + } + + void PromiseBuiltinsAssembler::BranchIfPromiseThenLookupChainIntact( +@@ -1174,7 +1174,7 @@ TF_BUILTIN(PromiseResolve, PromiseBuiltinsAssembler) { + LoadContextElement(native_context, Context::PROMISE_FUNCTION_INDEX); + GotoIfNot(WordEqual(LoadMapPrototype(value_map), promise_prototype), + &if_slow_constructor); +- GotoIf(IsSpeciesProtectorCellInvalid(), &if_slow_constructor); ++ GotoIf(IsPromiseSpeciesProtectorCellInvalid(), &if_slow_constructor); + + // If the {constructor} is the Promise function, we just immediately + // return the {value} here and don't bother wrapping it into a +diff --git a/src/builtins/builtins-typedarray-gen.cc b/src/builtins/builtins-typedarray-gen.cc +index 2a4f23b003..2316c7e8ca 100644 +--- a/src/builtins/builtins-typedarray-gen.cc ++++ b/src/builtins/builtins-typedarray-gen.cc +@@ -829,7 +829,7 @@ TNode TypedArrayBuiltinsAssembler::TypedArraySpeciesConstructor( + var_constructor = default_constructor; + Node* map = LoadMap(exemplar); + GotoIfNot(IsPrototypeTypedArrayPrototype(context, map), &slow); +- Branch(IsSpeciesProtectorCellInvalid(), &slow, &done); ++ Branch(IsTypedArraySpeciesProtectorCellInvalid(), &slow, &done); + + BIND(&slow); + var_constructor = +diff --git a/src/code-stub-assembler.cc b/src/code-stub-assembler.cc +index d3c81d0e81..f1ac210ce7 100644 +--- a/src/code-stub-assembler.cc ++++ b/src/code-stub-assembler.cc +@@ -997,7 +997,7 @@ void CodeStubAssembler::BranchIfFastJSArray(Node* object, Node* context, + void CodeStubAssembler::BranchIfFastJSArrayForCopy(Node* object, Node* context, + Label* if_true, + Label* if_false) { +- GotoIf(IsSpeciesProtectorCellInvalid(), if_false); ++ GotoIf(IsArraySpeciesProtectorCellInvalid(), if_false); + BranchIfFastJSArray(object, context, if_true, if_false); + } + +@@ -4354,9 +4354,23 @@ Node* CodeStubAssembler::IsPromiseThenProtectorCellInvalid() { + return WordEqual(cell_value, invalid); + } + +-Node* CodeStubAssembler::IsSpeciesProtectorCellInvalid() { ++Node* CodeStubAssembler::IsArraySpeciesProtectorCellInvalid() { + Node* invalid = SmiConstant(Isolate::kProtectorInvalid); +- Node* cell = LoadRoot(Heap::kSpeciesProtectorRootIndex); ++ Node* cell = LoadRoot(Heap::kArraySpeciesProtectorRootIndex); ++ Node* cell_value = LoadObjectField(cell, PropertyCell::kValueOffset); ++ return WordEqual(cell_value, invalid); ++} ++ ++Node* CodeStubAssembler::IsTypedArraySpeciesProtectorCellInvalid() { ++ Node* invalid = SmiConstant(Isolate::kProtectorInvalid); ++ Node* cell = LoadRoot(Heap::kTypedArraySpeciesProtectorRootIndex); ++ Node* cell_value = LoadObjectField(cell, PropertyCell::kValueOffset); ++ return WordEqual(cell_value, invalid); ++} ++ ++Node* CodeStubAssembler::IsPromiseSpeciesProtectorCellInvalid() { ++ Node* invalid = SmiConstant(Isolate::kProtectorInvalid); ++ Node* cell = LoadRoot(Heap::kPromiseSpeciesProtectorRootIndex); + Node* cell_value = LoadObjectField(cell, PropertyCell::kValueOffset); + return WordEqual(cell_value, invalid); + } +diff --git a/src/code-stub-assembler.h b/src/code-stub-assembler.h +index 8fca0b667f..47394a56ae 100644 +--- a/src/code-stub-assembler.h ++++ b/src/code-stub-assembler.h +@@ -22,48 +22,54 @@ class StubCache; + + enum class PrimitiveType { kBoolean, kNumber, kString, kSymbol }; + +-#define HEAP_CONSTANT_LIST(V) \ +- V(AccessorInfoMap, accessor_info_map, AccessorInfoMap) \ +- V(AccessorPairMap, accessor_pair_map, AccessorPairMap) \ +- V(AllocationSiteMap, allocation_site_map, AllocationSiteMap) \ +- V(BooleanMap, boolean_map, BooleanMap) \ +- V(CodeMap, code_map, CodeMap) \ +- V(EmptyPropertyDictionary, empty_property_dictionary, \ +- EmptyPropertyDictionary) \ +- V(EmptyFixedArray, empty_fixed_array, EmptyFixedArray) \ +- V(EmptySlowElementDictionary, empty_slow_element_dictionary, \ +- EmptySlowElementDictionary) \ +- V(empty_string, empty_string, EmptyString) \ +- V(EmptyWeakCell, empty_weak_cell, EmptyWeakCell) \ +- V(FalseValue, false_value, False) \ +- V(FeedbackVectorMap, feedback_vector_map, FeedbackVectorMap) \ +- V(FixedArrayMap, fixed_array_map, FixedArrayMap) \ +- V(FixedCOWArrayMap, fixed_cow_array_map, FixedCOWArrayMap) \ +- V(FixedDoubleArrayMap, fixed_double_array_map, FixedDoubleArrayMap) \ +- V(FunctionTemplateInfoMap, function_template_info_map, \ +- FunctionTemplateInfoMap) \ +- V(GlobalPropertyCellMap, global_property_cell_map, PropertyCellMap) \ +- V(has_instance_symbol, has_instance_symbol, HasInstanceSymbol) \ +- V(HeapNumberMap, heap_number_map, HeapNumberMap) \ +- V(length_string, length_string, LengthString) \ +- V(ManyClosuresCellMap, many_closures_cell_map, ManyClosuresCellMap) \ +- V(MetaMap, meta_map, MetaMap) \ +- V(MinusZeroValue, minus_zero_value, MinusZero) \ +- V(MutableHeapNumberMap, mutable_heap_number_map, MutableHeapNumberMap) \ +- V(NanValue, nan_value, Nan) \ +- V(NoClosuresCellMap, no_closures_cell_map, NoClosuresCellMap) \ +- V(NullValue, null_value, Null) \ +- V(OneClosureCellMap, one_closure_cell_map, OneClosureCellMap) \ +- V(prototype_string, prototype_string, PrototypeString) \ +- V(SpeciesProtector, species_protector, SpeciesProtector) \ +- V(StoreHandler0Map, store_handler0_map, StoreHandler0Map) \ +- V(SymbolMap, symbol_map, SymbolMap) \ +- V(TheHoleValue, the_hole_value, TheHole) \ +- V(TrueValue, true_value, True) \ +- V(Tuple2Map, tuple2_map, Tuple2Map) \ +- V(Tuple3Map, tuple3_map, Tuple3Map) \ +- V(UndefinedValue, undefined_value, Undefined) \ +- V(WeakCellMap, weak_cell_map, WeakCellMap) \ ++#define HEAP_CONSTANT_LIST(V) \ ++ V(AccessorInfoMap, accessor_info_map, AccessorInfoMap) \ ++ V(AccessorPairMap, accessor_pair_map, AccessorPairMap) \ ++ V(AllocationSiteMap, allocation_site_map, AllocationSiteMap) \ ++ V(BooleanMap, boolean_map, BooleanMap) \ ++ V(CodeMap, code_map, CodeMap) \ ++ V(EmptyPropertyDictionary, empty_property_dictionary, \ ++ EmptyPropertyDictionary) \ ++ V(EmptyFixedArray, empty_fixed_array, EmptyFixedArray) \ ++ V(EmptySlowElementDictionary, empty_slow_element_dictionary, \ ++ EmptySlowElementDictionary) \ ++ V(empty_string, empty_string, EmptyString) \ ++ V(EmptyWeakCell, empty_weak_cell, EmptyWeakCell) \ ++ V(FalseValue, false_value, False) \ ++ V(FeedbackVectorMap, feedback_vector_map, FeedbackVectorMap) \ ++ V(FixedArrayMap, fixed_array_map, FixedArrayMap) \ ++ V(FixedCOWArrayMap, fixed_cow_array_map, FixedCOWArrayMap) \ ++ V(FixedDoubleArrayMap, fixed_double_array_map, FixedDoubleArrayMap) \ ++ V(FunctionTemplateInfoMap, function_template_info_map, \ ++ FunctionTemplateInfoMap) \ ++ V(GlobalPropertyCellMap, global_property_cell_map, PropertyCellMap) \ ++ V(has_instance_symbol, has_instance_symbol, HasInstanceSymbol) \ ++ V(HeapNumberMap, heap_number_map, HeapNumberMap) \ ++ V(iterator_symbol, iterator_symbol, IteratorSymbol) \ ++ V(length_string, length_string, LengthString) \ ++ V(ManyClosuresCellMap, many_closures_cell_map, ManyClosuresCellMap) \ ++ V(MetaMap, meta_map, MetaMap) \ ++ V(MinusZeroValue, minus_zero_value, MinusZero) \ ++ V(MutableHeapNumberMap, mutable_heap_number_map, MutableHeapNumberMap) \ ++ V(NanValue, nan_value, Nan) \ ++ V(NoClosuresCellMap, no_closures_cell_map, NoClosuresCellMap) \ ++ V(NullValue, null_value, Null) \ ++ V(OneClosureCellMap, one_closure_cell_map, OneClosureCellMap) \ ++ V(prototype_string, prototype_string, PrototypeString) \ ++ V(ArraySpeciesProtector, array_species_protector, ArraySpeciesProtector) \ ++ V(TypedArraySpeciesProtector, typed_array_species_protector, \ ++ TypedArraySpeciesProtector) \ ++ V(PromiseSpeciesProtector, promise_species_protector, \ ++ PromiseSpeciesProtector) \ ++ V(StoreHandler0Map, store_handler0_map, StoreHandler0Map) \ ++ V(SymbolMap, symbol_map, SymbolMap) \ ++ V(TheHoleValue, the_hole_value, TheHole) \ ++ V(TransitionArrayMap, transition_array_map, TransitionArrayMap) \ ++ V(TrueValue, true_value, True) \ ++ V(Tuple2Map, tuple2_map, Tuple2Map) \ ++ V(Tuple3Map, tuple3_map, Tuple3Map) \ ++ V(UndefinedValue, undefined_value, Undefined) \ ++ V(WeakCellMap, weak_cell_map, WeakCellMap) \ + V(SharedFunctionInfoMap, shared_function_info_map, SharedFunctionInfoMap) + + // Returned from IteratorBuiltinsAssembler::GetIterator(). Struct is declared +@@ -1187,7 +1193,9 @@ class V8_EXPORT_PRIVATE CodeStubAssembler : public compiler::CodeAssembler { + } + + Node* IsPromiseThenProtectorCellInvalid(); +- Node* IsSpeciesProtectorCellInvalid(); ++ Node* IsArraySpeciesProtectorCellInvalid(); ++ Node* IsTypedArraySpeciesProtectorCellInvalid(); ++ Node* IsPromiseSpeciesProtectorCellInvalid(); + + // True iff |object| is a Smi or a HeapNumber. + Node* IsNumber(Node* object); +diff --git a/src/compiler/js-call-reducer.cc b/src/compiler/js-call-reducer.cc +index 417191c680..66ef88e650 100644 +--- a/src/compiler/js-call-reducer.cc ++++ b/src/compiler/js-call-reducer.cc +@@ -1453,7 +1453,7 @@ Reduction JSCallReducer::ReduceArrayMap(Node* node, + if (result == NodeProperties::kNoReceiverMaps) return NoChange(); + + // Ensure that any changes to the Array species constructor cause deopt. +- if (!isolate()->IsSpeciesLookupChainIntact()) return NoChange(); ++ if (!isolate()->IsArraySpeciesLookupChainIntact()) return NoChange(); + + const ElementsKind kind = receiver_maps[0]->elements_kind(); + +@@ -1464,7 +1464,7 @@ Reduction JSCallReducer::ReduceArrayMap(Node* node, + if (receiver_map->elements_kind() != kind) return NoChange(); + } + +- dependencies()->AssumePropertyCell(factory()->species_protector()); ++ dependencies()->AssumePropertyCell(factory()->array_species_protector()); + + Handle handle_constructor( + JSFunction::cast( +@@ -1653,7 +1653,7 @@ Reduction JSCallReducer::ReduceArrayFilter(Node* node, + if (result == NodeProperties::kNoReceiverMaps) return NoChange(); + + // And ensure that any changes to the Array species constructor cause deopt. +- if (!isolate()->IsSpeciesLookupChainIntact()) return NoChange(); ++ if (!isolate()->IsArraySpeciesLookupChainIntact()) return NoChange(); + + const ElementsKind kind = receiver_maps[0]->elements_kind(); + // The output array is packed (filter doesn't visit holes). +@@ -1668,7 +1668,7 @@ Reduction JSCallReducer::ReduceArrayFilter(Node* node, + if (receiver_map->elements_kind() != kind) return NoChange(); + } + +- dependencies()->AssumePropertyCell(factory()->species_protector()); ++ dependencies()->AssumePropertyCell(factory()->array_species_protector()); + + Handle initial_map( + Map::cast(native_context()->GetInitialJSArrayMap(packed_kind))); +@@ -2245,7 +2245,7 @@ Reduction JSCallReducer::ReduceArrayEvery(Node* node, + if (result == NodeProperties::kNoReceiverMaps) return NoChange(); + + // And ensure that any changes to the Array species constructor cause deopt. +- if (!isolate()->IsSpeciesLookupChainIntact()) return NoChange(); ++ if (!isolate()->IsArraySpeciesLookupChainIntact()) return NoChange(); + + const ElementsKind kind = receiver_maps[0]->elements_kind(); + +@@ -2256,7 +2256,7 @@ Reduction JSCallReducer::ReduceArrayEvery(Node* node, + if (receiver_map->elements_kind() != kind) return NoChange(); + } + +- dependencies()->AssumePropertyCell(factory()->species_protector()); ++ dependencies()->AssumePropertyCell(factory()->array_species_protector()); + + // If we have unreliable maps, we need a map check. + if (result == NodeProperties::kUnreliableReceiverMaps) { +@@ -2465,7 +2465,7 @@ Reduction JSCallReducer::ReduceArraySome(Node* node, + if (result == NodeProperties::kNoReceiverMaps) return NoChange(); + + // And ensure that any changes to the Array species constructor cause deopt. +- if (!isolate()->IsSpeciesLookupChainIntact()) return NoChange(); ++ if (!isolate()->IsArraySpeciesLookupChainIntact()) return NoChange(); + + if (receiver_maps.size() == 0) return NoChange(); + +@@ -2478,7 +2478,7 @@ Reduction JSCallReducer::ReduceArraySome(Node* node, + if (receiver_map->elements_kind() != kind) return NoChange(); + } + +- dependencies()->AssumePropertyCell(factory()->species_protector()); ++ dependencies()->AssumePropertyCell(factory()->array_species_protector()); + + Node* k = jsgraph()->ZeroConstant(); + +@@ -4997,7 +4997,7 @@ Reduction JSCallReducer::ReducePromisePrototypeFinally(Node* node) { + // lookup of "constructor" on JSPromise instances, whoch [[Prototype]] is + // the initial %PromisePrototype%, and the Symbol.species lookup on the + // %PromisePrototype%. +- if (!isolate()->IsSpeciesLookupChainIntact()) return NoChange(); ++ if (!isolate()->IsPromiseSpeciesLookupChainIntact()) return NoChange(); + + // Check if we know something about {receiver} already. + ZoneHandleSet receiver_maps; +@@ -5018,7 +5018,7 @@ Reduction JSCallReducer::ReducePromisePrototypeFinally(Node* node) { + // Add a code dependency on the necessary protectors. + dependencies()->AssumePropertyCell(factory()->promise_hook_protector()); + dependencies()->AssumePropertyCell(factory()->promise_then_protector()); +- dependencies()->AssumePropertyCell(factory()->species_protector()); ++ dependencies()->AssumePropertyCell(factory()->promise_species_protector()); + + // If the {receiver_maps} aren't reliable, we need to repeat the + // map check here, guarded by the CALL_IC. +@@ -5144,7 +5144,7 @@ Reduction JSCallReducer::ReducePromisePrototypeThen(Node* node) { + // guards the "constructor" lookup on all JSPromise instances and the + // initial Promise.prototype, as well as the Symbol.species lookup on + // the Promise constructor. +- if (!isolate()->IsSpeciesLookupChainIntact()) return NoChange(); ++ if (!isolate()->IsPromiseSpeciesLookupChainIntact()) return NoChange(); + + // Check if we know something about {receiver} already. + ZoneHandleSet receiver_maps; +@@ -5166,7 +5166,7 @@ Reduction JSCallReducer::ReducePromisePrototypeThen(Node* node) { + + // Add a code dependency on the necessary protectors. + dependencies()->AssumePropertyCell(factory()->promise_hook_protector()); +- dependencies()->AssumePropertyCell(factory()->species_protector()); ++ dependencies()->AssumePropertyCell(factory()->promise_species_protector()); + + // If the {receiver_maps} aren't reliable, we need to repeat the + // map check here, guarded by the CALL_IC. +diff --git a/src/heap/heap.h b/src/heap/heap.h +index 63bcfb2990..2bb2efc1be 100644 +--- a/src/heap/heap.h ++++ b/src/heap/heap.h +@@ -213,7 +213,9 @@ using v8::MemoryPressureLevel; + V(Cell, array_constructor_protector, ArrayConstructorProtector) \ + V(PropertyCell, no_elements_protector, NoElementsProtector) \ + V(Cell, is_concat_spreadable_protector, IsConcatSpreadableProtector) \ +- V(PropertyCell, species_protector, SpeciesProtector) \ ++ V(PropertyCell, array_species_protector, ArraySpeciesProtector) \ ++ V(PropertyCell, typed_array_species_protector, TypedArraySpeciesProtector) \ ++ V(PropertyCell, promise_species_protector, PromiseSpeciesProtector) \ + V(Cell, string_length_protector, StringLengthProtector) \ + V(Cell, fast_array_iteration_protector, FastArrayIterationProtector) \ + V(PropertyCell, array_iterator_protector, ArrayIteratorProtector) \ +@@ -378,7 +380,9 @@ using v8::MemoryPressureLevel; + V(SloppyArgumentsElementsMap) \ + V(SmallOrderedHashMapMap) \ + V(SmallOrderedHashSetMap) \ +- V(SpeciesProtector) \ ++ V(ArraySpeciesProtector) \ ++ V(TypedArraySpeciesProtector) \ ++ V(PromiseSpeciesProtector) \ + V(StaleRegister) \ + V(StringLengthProtector) \ + V(StringTableMap) \ +diff --git a/src/heap/setup-heap-internal.cc b/src/heap/setup-heap-internal.cc +index 8a7aca1694..f854594daa 100644 +--- a/src/heap/setup-heap-internal.cc ++++ b/src/heap/setup-heap-internal.cc +@@ -633,7 +633,15 @@ void Heap::CreateInitialObjects() { + + cell = factory->NewPropertyCell(factory->empty_string()); + cell->set_value(Smi::FromInt(Isolate::kProtectorValid)); +- set_species_protector(*cell); ++ set_array_species_protector(*cell); ++ ++ cell = factory->NewPropertyCell(factory->empty_string()); ++ cell->set_value(Smi::FromInt(Isolate::kProtectorValid)); ++ set_typed_array_species_protector(*cell); ++ ++ cell = factory->NewPropertyCell(factory->empty_string()); ++ cell->set_value(Smi::FromInt(Isolate::kProtectorValid)); ++ set_promise_species_protector(*cell); + + Handle string_length_overflow_cell = factory->NewCell( + handle(Smi::FromInt(Isolate::kProtectorValid), isolate())); +diff --git a/src/isolate-inl.h b/src/isolate-inl.h +index 9da1aa4110..7b4df21ad3 100644 +--- a/src/isolate-inl.h ++++ b/src/isolate-inl.h +@@ -131,7 +131,7 @@ bool Isolate::IsArrayConstructorIntact() { + return array_constructor_cell->value() == Smi::FromInt(kProtectorValid); + } + +-bool Isolate::IsSpeciesLookupChainIntact() { ++bool Isolate::IsArraySpeciesLookupChainIntact() { + // Note: It would be nice to have debug checks to make sure that the + // species protector is accurate, but this would be hard to do for most of + // what the protector stands for: +@@ -144,7 +144,19 @@ bool Isolate::IsSpeciesLookupChainIntact() { + // done here. In place, there are mjsunit tests harmony/array-species* which + // ensure that behavior is correct in various invalid protector cases. + +- PropertyCell* species_cell = heap()->species_protector(); ++ PropertyCell* species_cell = heap()->array_species_protector(); ++ return species_cell->value()->IsSmi() && ++ Smi::ToInt(species_cell->value()) == kProtectorValid; ++} ++ ++bool Isolate::IsTypedArraySpeciesLookupChainIntact() { ++ PropertyCell* species_cell = heap()->typed_array_species_protector(); ++ return species_cell->value()->IsSmi() && ++ Smi::ToInt(species_cell->value()) == kProtectorValid; ++} ++ ++bool Isolate::IsPromiseSpeciesLookupChainIntact() { ++ PropertyCell* species_cell = heap()->promise_species_protector(); + return species_cell->value()->IsSmi() && + Smi::ToInt(species_cell->value()) == kProtectorValid; + } +diff --git a/src/isolate.cc b/src/isolate.cc +index 21d932efea..7ed8e045b1 100644 +--- a/src/isolate.cc ++++ b/src/isolate.cc +@@ -3512,11 +3512,28 @@ void Isolate::InvalidateArrayConstructorProtector() { + DCHECK(!IsArrayConstructorIntact()); + } + +-void Isolate::InvalidateSpeciesProtector() { +- DCHECK(factory()->species_protector()->value()->IsSmi()); +- DCHECK(IsSpeciesLookupChainIntact()); +- factory()->species_protector()->set_value(Smi::FromInt(kProtectorInvalid)); +- DCHECK(!IsSpeciesLookupChainIntact()); ++void Isolate::InvalidateArraySpeciesProtector() { ++ DCHECK(factory()->array_species_protector()->value()->IsSmi()); ++ DCHECK(IsArraySpeciesLookupChainIntact()); ++ factory()->array_species_protector()->set_value( ++ Smi::FromInt(kProtectorInvalid)); ++ DCHECK(!IsArraySpeciesLookupChainIntact()); ++} ++ ++void Isolate::InvalidateTypedArraySpeciesProtector() { ++ DCHECK(factory()->typed_array_species_protector()->value()->IsSmi()); ++ DCHECK(IsTypedArraySpeciesLookupChainIntact()); ++ factory()->typed_array_species_protector()->set_value( ++ Smi::FromInt(kProtectorInvalid)); ++ DCHECK(!IsTypedArraySpeciesLookupChainIntact()); ++} ++ ++void Isolate::InvalidatePromiseSpeciesProtector() { ++ DCHECK(factory()->promise_species_protector()->value()->IsSmi()); ++ DCHECK(IsPromiseSpeciesLookupChainIntact()); ++ factory()->promise_species_protector()->set_value( ++ Smi::FromInt(kProtectorInvalid)); ++ DCHECK(!IsPromiseSpeciesLookupChainIntact()); + } + + void Isolate::InvalidateStringLengthOverflowProtector() { +diff --git a/src/isolate.h b/src/isolate.h +index 3f03e65fea..61814f6605 100644 +--- a/src/isolate.h ++++ b/src/isolate.h +@@ -1076,7 +1076,9 @@ class Isolate { + bool IsNoElementsProtectorIntact(Context* context); + bool IsNoElementsProtectorIntact(); + +- inline bool IsSpeciesLookupChainIntact(); ++ inline bool IsArraySpeciesLookupChainIntact(); ++ inline bool IsTypedArraySpeciesLookupChainIntact(); ++ inline bool IsPromiseSpeciesLookupChainIntact(); + bool IsIsConcatSpreadableLookupChainIntact(); + bool IsIsConcatSpreadableLookupChainIntact(JSReceiver* receiver); + inline bool IsStringLengthOverflowIntact(); +@@ -1112,7 +1114,9 @@ class Isolate { + UpdateNoElementsProtectorOnSetElement(object); + } + void InvalidateArrayConstructorProtector(); +- void InvalidateSpeciesProtector(); ++ void InvalidateArraySpeciesProtector(); ++ void InvalidateTypedArraySpeciesProtector(); ++ void InvalidatePromiseSpeciesProtector(); + void InvalidateIsConcatSpreadableProtector(); + void InvalidateStringLengthOverflowProtector(); + void InvalidateArrayIteratorProtector(); +diff --git a/src/lookup.cc b/src/lookup.cc +index 58ad9318dd..6de87cbbe9 100644 +--- a/src/lookup.cc ++++ b/src/lookup.cc +@@ -260,14 +260,27 @@ void LookupIterator::InternalUpdateProtector() { + if (isolate_->bootstrapper()->IsActive()) return; + + if (*name_ == heap()->constructor_string()) { +- if (!isolate_->IsSpeciesLookupChainIntact()) return; ++ if (!isolate_->IsArraySpeciesLookupChainIntact() && ++ !isolate_->IsTypedArraySpeciesLookupChainIntact() && ++ !isolate_->IsPromiseSpeciesLookupChainIntact()) ++ return; + // Setting the constructor property could change an instance's @@species +- if (holder_->IsJSArray() || holder_->IsJSPromise() || +- holder_->IsJSTypedArray()) { ++ if (holder_->IsJSArray()) { ++ if (!isolate_->IsArraySpeciesLookupChainIntact()) return; + isolate_->CountUsage( + v8::Isolate::UseCounterFeature::kArrayInstanceConstructorModified); +- isolate_->InvalidateSpeciesProtector(); +- } else if (holder_->map()->is_prototype_map()) { ++ isolate_->InvalidateArraySpeciesProtector(); ++ return; ++ } else if (holder_->IsJSPromise()) { ++ if (!isolate_->IsPromiseSpeciesLookupChainIntact()) return; ++ isolate_->InvalidatePromiseSpeciesProtector(); ++ return; ++ } else if (holder_->IsJSTypedArray()) { ++ if (!isolate_->IsTypedArraySpeciesLookupChainIntact()) return; ++ isolate_->InvalidateTypedArraySpeciesProtector(); ++ return; ++ } ++ if (holder_->map()->is_prototype_map()) { + DisallowHeapAllocation no_gc; + // Setting the constructor of Array.prototype, Promise.prototype or + // %TypedArray%.prototype of any realm also needs to invalidate the +@@ -276,26 +289,41 @@ void LookupIterator::InternalUpdateProtector() { + // have different prototypes for each type, and their parent prototype is + // pointing the same TYPED_ARRAY_PROTOTYPE. + if (isolate_->IsInAnyContext(*holder_, +- Context::INITIAL_ARRAY_PROTOTYPE_INDEX) || +- isolate_->IsInAnyContext(*holder_, +- Context::PROMISE_PROTOTYPE_INDEX) || +- isolate_->IsInAnyContext(holder_->map()->prototype(), +- Context::TYPED_ARRAY_PROTOTYPE_INDEX)) { +- isolate_->CountUsage(v8::Isolate::UseCounterFeature:: +- kArrayPrototypeConstructorModified); +- isolate_->InvalidateSpeciesProtector(); ++ Context::INITIAL_ARRAY_PROTOTYPE_INDEX)) { ++ if (!isolate_->IsArraySpeciesLookupChainIntact()) return; ++ isolate_->CountUsage( ++ v8::Isolate::UseCounterFeature::kArrayPrototypeConstructorModified); ++ isolate_->InvalidateArraySpeciesProtector(); ++ } else if (isolate_->IsInAnyContext(*holder_, ++ Context::PROMISE_PROTOTYPE_INDEX)) { ++ if (!isolate_->IsPromiseSpeciesLookupChainIntact()) return; ++ isolate_->InvalidatePromiseSpeciesProtector(); ++ } else if (isolate_->IsInAnyContext( ++ holder_->map()->prototype(), ++ Context::TYPED_ARRAY_PROTOTYPE_INDEX)) { ++ if (!isolate_->IsTypedArraySpeciesLookupChainIntact()) return; ++ isolate_->InvalidateTypedArraySpeciesProtector(); + } + } + } else if (*name_ == heap()->species_symbol()) { +- if (!isolate_->IsSpeciesLookupChainIntact()) return; ++ if (!isolate_->IsArraySpeciesLookupChainIntact() && ++ !isolate_->IsTypedArraySpeciesLookupChainIntact() && ++ !isolate_->IsPromiseSpeciesLookupChainIntact()) ++ return; + // Setting the Symbol.species property of any Array, Promise or TypedArray + // constructor invalidates the @@species protector +- if (isolate_->IsInAnyContext(*holder_, Context::ARRAY_FUNCTION_INDEX) || +- isolate_->IsInAnyContext(*holder_, Context::PROMISE_FUNCTION_INDEX) || +- IsTypedArrayFunctionInAnyContext(isolate_, *holder_)) { ++ if (isolate_->IsInAnyContext(*holder_, Context::ARRAY_FUNCTION_INDEX)) { ++ if (!isolate_->IsArraySpeciesLookupChainIntact()) return; + isolate_->CountUsage( + v8::Isolate::UseCounterFeature::kArraySpeciesModified); +- isolate_->InvalidateSpeciesProtector(); ++ isolate_->InvalidateArraySpeciesProtector(); ++ } else if (isolate_->IsInAnyContext(*holder_, ++ Context::PROMISE_FUNCTION_INDEX)) { ++ if (!isolate_->IsPromiseSpeciesLookupChainIntact()) return; ++ isolate_->InvalidatePromiseSpeciesProtector(); ++ } else if (IsTypedArrayFunctionInAnyContext(isolate_, *holder_)) { ++ if (!isolate_->IsTypedArraySpeciesLookupChainIntact()) return; ++ isolate_->InvalidateTypedArraySpeciesProtector(); + } + } else if (*name_ == heap()->is_concat_spreadable_symbol()) { + if (!isolate_->IsIsConcatSpreadableLookupChainIntact()) return; +diff --git a/src/objects.cc b/src/objects.cc +index 9e80224d93..b2c2274fcd 100644 +--- a/src/objects.cc ++++ b/src/objects.cc +@@ -2366,7 +2366,7 @@ MaybeHandle Object::ArraySpeciesConstructor( + Handle default_species = isolate->array_function(); + if (original_array->IsJSArray() && + Handle::cast(original_array)->HasArrayPrototype(isolate) && +- isolate->IsSpeciesLookupChainIntact()) { ++ isolate->IsArraySpeciesLookupChainIntact()) { + return default_species; + } + Handle constructor = isolate->factory()->undefined_value(); +diff --git a/src/runtime/runtime-array.cc b/src/runtime/runtime-array.cc +index 648606a274..f2f824ab21 100644 +--- a/src/runtime/runtime-array.cc ++++ b/src/runtime/runtime-array.cc +@@ -391,7 +391,7 @@ RUNTIME_FUNCTION(Runtime_TrySliceSimpleNonFastElements) { + // implementation. + if (receiver->IsJSArray()) { + // This "fastish" path must make sure the destination array is a JSArray. +- if (!isolate->IsSpeciesLookupChainIntact() || ++ if (!isolate->IsArraySpeciesLookupChainIntact() || + !JSArray::cast(*receiver)->HasArrayPrototype(isolate)) { + return Smi::FromInt(0); + } +diff --git a/src/runtime/runtime-test.cc b/src/runtime/runtime-test.cc +index 6b2f3467fc..6192747ab2 100644 +--- a/src/runtime/runtime-test.cc ++++ b/src/runtime/runtime-test.cc +@@ -839,11 +839,24 @@ TYPED_ARRAYS(FIXED_TYPED_ARRAYS_CHECK_RUNTIME_FUNCTION) + + #undef FIXED_TYPED_ARRAYS_CHECK_RUNTIME_FUNCTION + ++RUNTIME_FUNCTION(Runtime_ArraySpeciesProtector) { ++ SealHandleScope shs(isolate); ++ DCHECK_EQ(0, args.length()); ++ return isolate->heap()->ToBoolean(isolate->IsArraySpeciesLookupChainIntact()); ++} + +-RUNTIME_FUNCTION(Runtime_SpeciesProtector) { ++RUNTIME_FUNCTION(Runtime_TypedArraySpeciesProtector) { + SealHandleScope shs(isolate); + DCHECK_EQ(0, args.length()); +- return isolate->heap()->ToBoolean(isolate->IsSpeciesLookupChainIntact()); ++ return isolate->heap()->ToBoolean( ++ isolate->IsTypedArraySpeciesLookupChainIntact()); ++} ++ ++RUNTIME_FUNCTION(Runtime_PromiseSpeciesProtector) { ++ SealHandleScope shs(isolate); ++ DCHECK_EQ(0, args.length()); ++ return isolate->heap()->ToBoolean( ++ isolate->IsPromiseSpeciesLookupChainIntact()); + } + + // Take a compiled wasm module, serialize it and copy the buffer into an array +diff --git a/src/runtime/runtime.h b/src/runtime/runtime.h +index 2bfd280803..b196da83b5 100644 +--- a/src/runtime/runtime.h ++++ b/src/runtime/runtime.h +@@ -587,7 +587,9 @@ namespace internal { + F(SetForceSlowPath, 1, 1) \ + F(SetWasmCompileControls, 2, 1) \ + F(SetWasmInstantiateControls, 0, 1) \ +- F(SpeciesProtector, 0, 1) \ ++ F(ArraySpeciesProtector, 0, 1) \ ++ F(TypedArraySpeciesProtector, 0, 1) \ ++ F(PromiseSpeciesProtector, 0, 1) \ + F(SystemBreak, 0, 1) \ + F(TraceEnter, 0, 1) \ + F(TraceExit, 1, 1) \ +diff --git a/test/cctest/test-typedarrays.cc b/test/cctest/test-typedarrays.cc +index 7ec9197b65..bab6e0f2f6 100644 +--- a/test/cctest/test-typedarrays.cc ++++ b/test/cctest/test-typedarrays.cc +@@ -117,12 +117,12 @@ void TestSpeciesProtector(char* code, + + v8::internal::Isolate* i_isolate = + reinterpret_cast(isolate); +- CHECK(i_isolate->IsSpeciesLookupChainIntact()); ++ CHECK(i_isolate->IsTypedArraySpeciesLookupChainIntact()); + CompileRun(code); + if (invalidates_species_protector) { +- CHECK(!i_isolate->IsSpeciesLookupChainIntact()); ++ CHECK(!i_isolate->IsTypedArraySpeciesLookupChainIntact()); + } else { +- CHECK(i_isolate->IsSpeciesLookupChainIntact()); ++ CHECK(i_isolate->IsTypedArraySpeciesLookupChainIntact()); + } + + v8::Local my_typed_array = CompileRun("MyTypedArray"); +diff --git a/test/mjsunit/es6/array-species-constructor-accessor.js b/test/mjsunit/es6/array-species-constructor-accessor.js +index 7ebf328a8a..7185d98b58 100644 +--- a/test/mjsunit/es6/array-species-constructor-accessor.js ++++ b/test/mjsunit/es6/array-species-constructor-accessor.js +@@ -18,7 +18,7 @@ assertEquals(1, x.concat([1])[0]); + class MyArray extends Array { } + + Object.defineProperty(x, 'constructor', {get() { return MyArray; }}); +-assertFalse(%SpeciesProtector()); ++assertFalse(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/es6/array-species-constructor-delete.js b/test/mjsunit/es6/array-species-constructor-delete.js +index fff22a2a8c..3b85d52565 100644 +--- a/test/mjsunit/es6/array-species-constructor-delete.js ++++ b/test/mjsunit/es6/array-species-constructor-delete.js +@@ -19,7 +19,7 @@ class MyArray extends Array { } + + Object.prototype.constructor = MyArray; + delete Array.prototype.constructor; +-assertFalse(%SpeciesProtector()); ++assertFalse(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/es6/array-species-constructor.js b/test/mjsunit/es6/array-species-constructor.js +index 0d888f46ee..07e897d458 100644 +--- a/test/mjsunit/es6/array-species-constructor.js ++++ b/test/mjsunit/es6/array-species-constructor.js +@@ -18,7 +18,7 @@ assertEquals(1, x.concat([1])[0]); + class MyArray extends Array { } + + x.constructor = MyArray; +-assertFalse(%SpeciesProtector()); ++assertFalse(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/es6/array-species-delete.js b/test/mjsunit/es6/array-species-delete.js +index 16a2fa26f9..2f0f50a1b2 100644 +--- a/test/mjsunit/es6/array-species-delete.js ++++ b/test/mjsunit/es6/array-species-delete.js +@@ -19,7 +19,7 @@ class MyArray extends Array { } + + Object.prototype[Symbol.species] = MyArray; + delete Array[Symbol.species]; +-assertFalse(%SpeciesProtector()); ++assertFalse(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/es6/array-species-modified.js b/test/mjsunit/es6/array-species-modified.js +index 58feb31669..d5a707997a 100644 +--- a/test/mjsunit/es6/array-species-modified.js ++++ b/test/mjsunit/es6/array-species-modified.js +@@ -18,7 +18,7 @@ assertEquals(1, x.concat([1])[0]); + class MyArray extends Array { } + + Object.defineProperty(Array, Symbol.species, {value: MyArray}); +-assertFalse(%SpeciesProtector()); ++assertFalse(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/es6/array-species-parent-constructor.js b/test/mjsunit/es6/array-species-parent-constructor.js +index b4fb1d56e3..8a861fb05d 100644 +--- a/test/mjsunit/es6/array-species-parent-constructor.js ++++ b/test/mjsunit/es6/array-species-parent-constructor.js +@@ -18,7 +18,7 @@ assertEquals(1, x.concat([1])[0]); + class MyArray extends Array { } + + Array.prototype.constructor = MyArray; +-assertFalse(%SpeciesProtector()); ++assertFalse(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/es6/array-species-proto.js b/test/mjsunit/es6/array-species-proto.js +index 6b55881cd6..d8e2ae5ddd 100644 +--- a/test/mjsunit/es6/array-species-proto.js ++++ b/test/mjsunit/es6/array-species-proto.js +@@ -18,7 +18,7 @@ assertEquals(1, x.concat([1])[0]); + class MyArray extends Array { } + + x.__proto__ = MyArray.prototype; +-assertTrue(%SpeciesProtector()); ++assertTrue(%ArraySpeciesProtector()); + + assertEquals(MyArray, x.map(()=>{}).constructor); + assertEquals(MyArray, x.filter(()=>{}).constructor); +diff --git a/test/mjsunit/harmony/regexp-named-captures.js b/test/mjsunit/harmony/regexp-named-captures.js +index 72041b99bf..aab8393392 100644 +--- a/test/mjsunit/harmony/regexp-named-captures.js ++++ b/test/mjsunit/harmony/regexp-named-captures.js +@@ -425,7 +425,7 @@ function toSlowMode(re) { + { + const re = /./; + const result = re.exec("a"); +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals(result.__proto__, Array.prototype); + assertTrue(result.hasOwnProperty('groups')); + assertArrayEquals(["a"], result); +@@ -433,7 +433,7 @@ function toSlowMode(re) { + assertEquals(undefined, result.groups); + + Array.prototype.groups = { a: "b" }; +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals("$", "a".replace(re, "$")); + Array.prototype.groups = undefined; + } +@@ -441,7 +441,7 @@ function toSlowMode(re) { + { + const re = toSlowMode(/./); + const result = re.exec("a"); +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals(result.__proto__, Array.prototype); + assertTrue(result.hasOwnProperty('groups')); + assertArrayEquals(["a"], result); +@@ -449,7 +449,7 @@ function toSlowMode(re) { + assertEquals(undefined, result.groups); + + Array.prototype.groups = { a: "b" }; +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals("$", "a".replace(re, "$")); + Array.prototype.groups = undefined; + } +@@ -457,7 +457,7 @@ function toSlowMode(re) { + { + const re = /(?a).|(?x)/; + const result = re.exec("ab"); +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals(result.__proto__, Array.prototype); + assertTrue(result.hasOwnProperty('groups')); + assertArrayEquals(["ab", "a", undefined], result); +@@ -467,7 +467,7 @@ function toSlowMode(re) { + // a is a matched named capture, b is an unmatched named capture, and z + // is not a named capture. + Array.prototype.groups = { a: "b", x: "y", z: "z" }; +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals("a", "ab".replace(re, "$")); + assertEquals("", "ab".replace(re, "$")); + assertEquals("", "ab".replace(re, "$")); +@@ -477,7 +477,7 @@ function toSlowMode(re) { + { + const re = toSlowMode(/(?a).|(?x)/); + const result = re.exec("ab"); +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals(result.__proto__, Array.prototype); + assertTrue(result.hasOwnProperty('groups')); + assertArrayEquals(["ab", "a", undefined], result); +@@ -487,7 +487,7 @@ function toSlowMode(re) { + // a is a matched named capture, b is an unmatched named capture, and z + // is not a named capture. + Array.prototype.groups = { a: "b", x: "y", z: "z" }; +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals("a", "ab".replace(re, "$")); + assertEquals("", "ab".replace(re, "$")); + assertEquals("", "ab".replace(re, "$")); +@@ -506,13 +506,13 @@ function toSlowMode(re) { + + const re = new FakeRegExp(); + const result = re.exec("ab"); +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals(result.__proto__, Array.prototype); + assertFalse(result.hasOwnProperty('groups')); + + Array.prototype.groups = { a: "b" }; + Array.prototype.groups.__proto__.b = "c"; +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals("b", "ab".replace(re, "$")); + assertEquals("c", "ab".replace(re, "$")); + Array.prototype.groups = undefined; +@@ -531,7 +531,7 @@ function toSlowMode(re) { + + const re = new FakeRegExp(); + const result = re.exec("ab"); +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + assertEquals(result.__proto__, Array.prototype); + assertTrue(result.hasOwnProperty('groups')); + assertEquals({ a: "b" }, result.groups); +diff --git a/test/mjsunit/keyed-store-generic.js b/test/mjsunit/keyed-store-generic.js +index c2c48dd96d..e5d6ab41f2 100644 +--- a/test/mjsunit/keyed-store-generic.js ++++ b/test/mjsunit/keyed-store-generic.js +@@ -16,7 +16,7 @@ f("make it generic", 0, 0); + + (function TestSpeciesProtector() { + function MyArray() {} +- assertTrue(%SpeciesProtector()); ++ assertTrue(%ArraySpeciesProtector()); + f(Array.prototype, "constructor", MyArray); +- assertFalse(%SpeciesProtector()); ++ assertFalse(%ArraySpeciesProtector()); + })(); +diff --git a/tools/v8heapconst.py b/tools/v8heapconst.py +index 5659cdd03c..b4a98dcc11 100644 +--- a/tools/v8heapconst.py ++++ b/tools/v8heapconst.py +@@ -322,34 +322,35 @@ KNOWN_OBJECTS = { + ("OLD_SPACE", 0x02519): "TerminationException", + ("OLD_SPACE", 0x02579): "OptimizedOut", + ("OLD_SPACE", 0x025d1): "StaleRegister", +- ("OLD_SPACE", 0x02651): "EmptyByteArray", +- ("OLD_SPACE", 0x02661): "EmptyFixedUint8Array", +- ("OLD_SPACE", 0x02681): "EmptyFixedInt8Array", +- ("OLD_SPACE", 0x026a1): "EmptyFixedUint16Array", +- ("OLD_SPACE", 0x026c1): "EmptyFixedInt16Array", +- ("OLD_SPACE", 0x026e1): "EmptyFixedUint32Array", +- ("OLD_SPACE", 0x02701): "EmptyFixedInt32Array", +- ("OLD_SPACE", 0x02721): "EmptyFixedFloat32Array", +- ("OLD_SPACE", 0x02741): "EmptyFixedFloat64Array", +- ("OLD_SPACE", 0x02761): "EmptyFixedUint8ClampedArray", +- ("OLD_SPACE", 0x027c1): "EmptyScript", +- ("OLD_SPACE", 0x02849): "ManyClosuresCell", +- ("OLD_SPACE", 0x02859): "EmptySloppyArgumentsElements", +- ("OLD_SPACE", 0x02879): "EmptySlowElementDictionary", +- ("OLD_SPACE", 0x028c1): "EmptyOrderedHashMap", +- ("OLD_SPACE", 0x028e9): "EmptyOrderedHashSet", +- ("OLD_SPACE", 0x02911): "EmptyPropertyCell", +- ("OLD_SPACE", 0x02939): "EmptyWeakCell", +- ("OLD_SPACE", 0x029a9): "NoElementsProtector", +- ("OLD_SPACE", 0x029d1): "IsConcatSpreadableProtector", +- ("OLD_SPACE", 0x029e1): "SpeciesProtector", +- ("OLD_SPACE", 0x02a09): "StringLengthProtector", +- ("OLD_SPACE", 0x02a19): "FastArrayIterationProtector", +- ("OLD_SPACE", 0x02a29): "ArrayIteratorProtector", +- ("OLD_SPACE", 0x02a51): "ArrayBufferNeuteringProtector", +- ("OLD_SPACE", 0x02ac9): "InfinityValue", +- ("OLD_SPACE", 0x02ad9): "MinusZeroValue", +- ("OLD_SPACE", 0x02ae9): "MinusInfinityValue", ++ ("OLD_SPACE", 0x02661): "EmptyByteArray", ++ ("OLD_SPACE", 0x02681): "EmptyFixedUint8Array", ++ ("OLD_SPACE", 0x026a1): "EmptyFixedInt8Array", ++ ("OLD_SPACE", 0x026c1): "EmptyFixedUint16Array", ++ ("OLD_SPACE", 0x026e1): "EmptyFixedInt16Array", ++ ("OLD_SPACE", 0x02701): "EmptyFixedUint32Array", ++ ("OLD_SPACE", 0x02721): "EmptyFixedInt32Array", ++ ("OLD_SPACE", 0x02741): "EmptyFixedFloat32Array", ++ ("OLD_SPACE", 0x02761): "EmptyFixedFloat64Array", ++ ("OLD_SPACE", 0x02781): "EmptyFixedUint8ClampedArray", ++ ("OLD_SPACE", 0x027e1): "EmptyScript", ++ ("OLD_SPACE", 0x02879): "ManyClosuresCell", ++ ("OLD_SPACE", 0x02889): "EmptySloppyArgumentsElements", ++ ("OLD_SPACE", 0x028a9): "EmptySlowElementDictionary", ++ ("OLD_SPACE", 0x028f1): "EmptyOrderedHashMap", ++ ("OLD_SPACE", 0x02919): "EmptyOrderedHashSet", ++ ("OLD_SPACE", 0x02951): "EmptyPropertyCell", ++ ("OLD_SPACE", 0x02979): "EmptyWeakCell", ++ ("OLD_SPACE", 0x029e9): "NoElementsProtector", ++ ("OLD_SPACE", 0x02a11): "IsConcatSpreadableProtector", ++ ("OLD_SPACE", 0x02a21): "ArraySpeciesProtector", ++ ("OLD_SPACE", 0x02a49): "TypedArraySpeciesProtector", ++ ("OLD_SPACE", 0x02a71): "PromiseSpeciesProtector", ++ ("OLD_SPACE", 0x02a99): "StringLengthProtector", ++ ("OLD_SPACE", 0x02aa9): "ArrayIteratorProtector", ++ ("OLD_SPACE", 0x02ad1): "ArrayBufferNeuteringProtector", ++ ("OLD_SPACE", 0x02b59): "InfinityValue", ++ ("OLD_SPACE", 0x02b69): "MinusZeroValue", ++ ("OLD_SPACE", 0x02b79): "MinusInfinityValue", + } + + # List of known V8 Frame Markers. +-- +2.11.0 (Apple Git-81) + diff --git a/patches/common/v8/backport_39d546a.patch b/patches/common/v8/backport_39d546a.patch new file mode 100644 index 00000000000..fc9daca5a98 --- /dev/null +++ b/patches/common/v8/backport_39d546a.patch @@ -0,0 +1,84 @@ +39d546a24022b62b00aedf7b556ac6c9e2306aab +diff --git a/AUTHORS b/AUTHORS +index 3251716f2a..4b5163961d 100644 +--- a/AUTHORS ++++ b/AUTHORS +@@ -70,6 +70,7 @@ Felix Geisendörfer + Filipe David Manana + Franziska Hinkelmann + Geoffrey Garside ++Gus Caplan + Gwang Yoon Hwang + Henrique Ferreiro + Hirofumi Mako +diff --git a/include/v8.h b/include/v8.h +index 573e80176d..aeeebba304 100644 +--- a/include/v8.h ++++ b/include/v8.h +@@ -2378,6 +2378,11 @@ class V8_EXPORT Value : public Data { + + bool IsWebAssemblyCompiledModule() const; + ++ /** ++ * Returns true if the value is a Module Namespace Object. ++ */ ++ bool IsModuleNamespaceObject() const; ++ + V8_WARN_UNUSED_RESULT MaybeLocal ToBigInt( + Local context) const; + V8_WARN_UNUSED_RESULT MaybeLocal ToBoolean( +diff --git a/src/api.cc b/src/api.cc +index 8b177d041d..6dd669ee11 100644 +--- a/src/api.cc ++++ b/src/api.cc +@@ -3583,6 +3583,10 @@ bool Value::IsSetIterator() const { + + bool Value::IsPromise() const { return Utils::OpenHandle(this)->IsJSPromise(); } + ++bool Value::IsModuleNamespaceObject() const { ++ return Utils::OpenHandle(this)->IsJSModuleNamespace(); ++} ++ + MaybeLocal Value::ToString(Local context) const { + auto obj = Utils::OpenHandle(this); + if (obj->IsString()) return ToApiHandle(obj); +diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc +index 54afc61f4c..b7483a7c5e 100644 +--- a/test/cctest/test-api.cc ++++ b/test/cctest/test-api.cc +@@ -27239,6 +27239,35 @@ TEST(ImportMeta) { + CHECK(result->StrictEquals(Local::Cast(v8::Utils::ToLocal(meta)))); + } + ++TEST(GetModuleNamespace) { ++ LocalContext context; ++ v8::Isolate* isolate = context->GetIsolate(); ++ v8::HandleScope scope(isolate); ++ ++ Local url = v8_str("www.google.com"); ++ Local source_text = v8_str("export default 5; export const a = 10;"); ++ v8::ScriptOrigin origin(url, Local(), Local(), ++ Local(), Local(), ++ Local(), Local(), ++ Local(), True(isolate)); ++ v8::ScriptCompiler::Source source(source_text, origin); ++ Local module = ++ v8::ScriptCompiler::CompileModule(isolate, &source).ToLocalChecked(); ++ module->InstantiateModule(context.local(), UnexpectedModuleResolveCallback) ++ .ToChecked(); ++ module->Evaluate(context.local()).ToLocalChecked(); ++ ++ Local ns_val = module->GetModuleNamespace(); ++ CHECK(ns_val->IsModuleNamespaceObject()); ++ Local ns = ns_val.As(); ++ CHECK(ns->Get(context.local(), v8_str("default")) ++ .ToLocalChecked() ++ ->StrictEquals(v8::Number::New(isolate, 5))); ++ CHECK(ns->Get(context.local(), v8_str("a")) ++ .ToLocalChecked() ++ ->StrictEquals(v8::Number::New(isolate, 10))); ++} ++ + TEST(GlobalTemplateWithDoubleProperty) { + v8::Isolate* isolate = CcTest::isolate(); + v8::HandleScope handle_scope(isolate); diff --git a/patches/common/v8/backport_50206308.patch b/patches/common/v8/backport_50206308.patch new file mode 100644 index 00000000000..539d49c9718 --- /dev/null +++ b/patches/common/v8/backport_50206308.patch @@ -0,0 +1,235 @@ +From 5020630808043615f2f6fbbfba1ea73342bebd69 Mon Sep 17 00:00:00 2001 +From: Daniel Clifford +Date: Wed, 28 Mar 2018 13:30:16 +0200 +Subject: [PATCH] Remove legacy C++ implementation of Array#slice + +Change-Id: Ifdeda00ad55aa937a6a414e7e566e6640ccd83c0 +Reviewed-on: https://chromium-review.googlesource.com/980936 +Reviewed-by: Yang Guo +Commit-Queue: Daniel Clifford +Cr-Commit-Position: refs/heads/master@{#52278} +--- + src/bootstrapper.cc | 8 ++--- + src/builtins/builtins-array.cc | 69 ------------------------------------- + src/builtins/builtins-definitions.h | 1 - + src/contexts.h | 1 - + src/debug/debug-evaluate.cc | 1 - + src/flag-definitions.h | 2 +- + src/js/array.js | 43 +++-------------------- + 7 files changed, 8 insertions(+), 117 deletions(-) + +diff --git a/src/bootstrapper.cc b/src/bootstrapper.cc +index 95d98078f3..626251202d 100644 +--- a/src/bootstrapper.cc ++++ b/src/bootstrapper.cc +@@ -1658,12 +1658,8 @@ void Genesis::InitializeGlobal(Handle global_object, + SimpleInstallFunction(proto, "shift", Builtins::kArrayPrototypeShift, 0, + false); + SimpleInstallFunction(proto, "unshift", Builtins::kArrayUnshift, 1, false); +- if (FLAG_enable_experimental_builtins) { +- SimpleInstallFunction(proto, "slice", Builtins::kArrayPrototypeSlice, 2, +- false); +- } else { +- SimpleInstallFunction(proto, "slice", Builtins::kArraySlice, 2, false); +- } ++ SimpleInstallFunction(proto, "slice", Builtins::kArrayPrototypeSlice, 2, ++ false); + SimpleInstallFunction(proto, "splice", Builtins::kArraySplice, 2, false); + SimpleInstallFunction(proto, "includes", Builtins::kArrayIncludes, 1, + false); +diff --git a/src/builtins/builtins-array.cc b/src/builtins/builtins-array.cc +index f400e824f0..7e3f948cbe 100644 +--- a/src/builtins/builtins-array.cc ++++ b/src/builtins/builtins-array.cc +@@ -240,75 +240,6 @@ BUILTIN(ArrayUnshift) { + return Smi::FromInt(new_length); + } + +-BUILTIN(ArraySlice) { +- HandleScope scope(isolate); +- Handle receiver = args.receiver(); +- int len = -1; +- int relative_start = 0; +- int relative_end = 0; +- +- if (receiver->IsJSArray()) { +- DisallowHeapAllocation no_gc; +- JSArray* array = JSArray::cast(*receiver); +- if (V8_UNLIKELY(!array->HasFastElements() || +- !IsJSArrayFastElementMovingAllowed(isolate, array) || +- !isolate->IsSpeciesLookupChainIntact() || +- // If this is a subclass of Array, then call out to JS +- !array->HasArrayPrototype(isolate))) { +- AllowHeapAllocation allow_allocation; +- return CallJsIntrinsic(isolate, isolate->array_slice(), args); +- } +- len = Smi::ToInt(array->length()); +- } else if (receiver->IsJSObject() && +- JSSloppyArgumentsObject::GetSloppyArgumentsLength( +- isolate, Handle::cast(receiver), &len)) { +- // Array.prototype.slice.call(arguments, ...) is quite a common idiom +- // (notably more than 50% of invocations in Web apps). +- // Treat it in C++ as well. +- DCHECK(JSObject::cast(*receiver)->HasFastElements() || +- JSObject::cast(*receiver)->HasFastArgumentsElements()); +- } else { +- AllowHeapAllocation allow_allocation; +- return CallJsIntrinsic(isolate, isolate->array_slice(), args); +- } +- DCHECK_LE(0, len); +- int argument_count = args.length() - 1; +- // Note carefully chosen defaults---if argument is missing, +- // it's undefined which gets converted to 0 for relative_start +- // and to len for relative_end. +- relative_start = 0; +- relative_end = len; +- if (argument_count > 0) { +- DisallowHeapAllocation no_gc; +- if (!ClampedToInteger(isolate, args[1], &relative_start)) { +- AllowHeapAllocation allow_allocation; +- return CallJsIntrinsic(isolate, isolate->array_slice(), args); +- } +- if (argument_count > 1) { +- Object* end_arg = args[2]; +- // slice handles the end_arg specially +- if (end_arg->IsUndefined(isolate)) { +- relative_end = len; +- } else if (!ClampedToInteger(isolate, end_arg, &relative_end)) { +- AllowHeapAllocation allow_allocation; +- return CallJsIntrinsic(isolate, isolate->array_slice(), args); +- } +- } +- } +- +- // ECMAScript 232, 3rd Edition, Section 15.4.4.10, step 6. +- uint32_t actual_start = (relative_start < 0) ? Max(len + relative_start, 0) +- : Min(relative_start, len); +- +- // ECMAScript 232, 3rd Edition, Section 15.4.4.10, step 8. +- uint32_t actual_end = +- (relative_end < 0) ? Max(len + relative_end, 0) : Min(relative_end, len); +- +- Handle object = Handle::cast(receiver); +- ElementsAccessor* accessor = object->GetElementsAccessor(); +- return *accessor->Slice(object, actual_start, actual_end); +-} +- + BUILTIN(ArraySplice) { + HandleScope scope(isolate); + Handle receiver = args.receiver(); +diff --git a/src/builtins/builtins-definitions.h b/src/builtins/builtins-definitions.h +index f31cf707cb..5d2b160f78 100644 +--- a/src/builtins/builtins-definitions.h ++++ b/src/builtins/builtins-definitions.h +@@ -269,7 +269,6 @@ namespace internal { + CPP(ArrayShift) \ + TFJ(ArrayPrototypeShift, SharedFunctionInfo::kDontAdaptArgumentsSentinel) \ + /* ES6 #sec-array.prototype.slice */ \ +- CPP(ArraySlice) \ + TFJ(ArrayPrototypeSlice, SharedFunctionInfo::kDontAdaptArgumentsSentinel) \ + /* ES6 #sec-array.prototype.splice */ \ + CPP(ArraySplice) \ +diff --git a/src/contexts.h b/src/contexts.h +index 03b32ab586..bb55d91c9c 100644 +--- a/src/contexts.h ++++ b/src/contexts.h +@@ -69,7 +69,6 @@ enum ContextLookupFlags { + V(ARRAY_PUSH_INDEX, JSFunction, array_push) \ + V(ARRAY_SHIFT_INDEX, JSFunction, array_shift) \ + V(ARRAY_SPLICE_INDEX, JSFunction, array_splice) \ +- V(ARRAY_SLICE_INDEX, JSFunction, array_slice) \ + V(ARRAY_UNSHIFT_INDEX, JSFunction, array_unshift) \ + V(ARRAY_ENTRIES_ITERATOR_INDEX, JSFunction, array_entries_iterator) \ + V(ARRAY_FOR_EACH_ITERATOR_INDEX, JSFunction, array_for_each_iterator) \ +diff --git a/src/debug/debug-evaluate.cc b/src/debug/debug-evaluate.cc +index c937be4fe0..d9defc778c 100644 +--- a/src/debug/debug-evaluate.cc ++++ b/src/debug/debug-evaluate.cc +@@ -616,7 +616,6 @@ bool BuiltinHasNoSideEffect(Builtins::Name id) { + case Builtins::kArrayEvery: + case Builtins::kArraySome: + case Builtins::kArrayConcat: +- case Builtins::kArraySlice: + case Builtins::kArrayFilter: + case Builtins::kArrayMap: + case Builtins::kArrayReduce: +diff --git a/src/flag-definitions.h b/src/flag-definitions.h +index 21cd9b2d3c..a05571700f 100644 +--- a/src/flag-definitions.h ++++ b/src/flag-definitions.h +@@ -832,7 +832,7 @@ DEFINE_BOOL(expose_trigger_failure, false, "expose trigger-failure extension") + DEFINE_INT(stack_trace_limit, 10, "number of stack frames to capture") + DEFINE_BOOL(builtins_in_stack_traces, false, + "show built-in functions in stack traces") +-DEFINE_BOOL(enable_experimental_builtins, true, ++DEFINE_BOOL(enable_experimental_builtins, false, + "enable new csa-based experimental builtins") + DEFINE_BOOL(disallow_code_generation_from_strings, false, + "disallow eval and friends") +diff --git a/src/js/array.js b/src/js/array.js +index c293f8e8c8..5b393263da 100644 +--- a/src/js/array.js ++++ b/src/js/array.js +@@ -578,46 +578,14 @@ function ArrayUnshiftFallback(arg1) { // length == 1 + } + + ++// Oh the humanity... don't remove the following function because js2c for some ++// reason gets symbol minifiation wrong if it's not there. Instead of spending ++// the time fixing js2c (which will go away when all of the internal .js runtime ++// files are gone), just keep this work-around. + function ArraySliceFallback(start, end) { +- var array = TO_OBJECT(this); +- var len = TO_LENGTH(array.length); +- var start_i = TO_INTEGER(start); +- var end_i = len; +- +- if (!IS_UNDEFINED(end)) end_i = TO_INTEGER(end); +- +- if (start_i < 0) { +- start_i += len; +- if (start_i < 0) start_i = 0; +- } else { +- if (start_i > len) start_i = len; +- } +- +- if (end_i < 0) { +- end_i += len; +- if (end_i < 0) end_i = 0; +- } else { +- if (end_i > len) end_i = len; +- } +- +- var result = ArraySpeciesCreate(array, MathMax(end_i - start_i, 0)); +- +- if (end_i < start_i) return result; +- +- if (UseSparseVariant(array, len, IS_ARRAY(array), end_i - start_i)) { +- %NormalizeElements(array); +- if (IS_ARRAY(result)) %NormalizeElements(result); +- SparseSlice(array, start_i, end_i - start_i, len, result); +- } else { +- SimpleSlice(array, start_i, end_i - start_i, len, result); +- } +- +- result.length = end_i - start_i; +- +- return result; ++ return null; + } + +- + function ComputeSpliceStartIndex(start_i, len) { + if (start_i < 0) { + start_i += len; +@@ -1229,7 +1197,6 @@ utils.Export(function(to) { + "array_push", ArrayPushFallback, + "array_shift", ArrayShiftFallback, + "array_splice", ArraySpliceFallback, +- "array_slice", ArraySliceFallback, + "array_unshift", ArrayUnshiftFallback, + ]); + +-- +2.11.0 (Apple Git-81) + diff --git a/patches/common/v8/backport_91ddb65d.patch b/patches/common/v8/backport_91ddb65d.patch new file mode 100644 index 00000000000..09d5b0facc7 --- /dev/null +++ b/patches/common/v8/backport_91ddb65d.patch @@ -0,0 +1,2330 @@ +diff --git a/src/bootstrapper.cc b/src/bootstrapper.cc +index 43c7527de98..2138b9c73d7 100644 +--- a/src/bootstrapper.cc ++++ b/src/bootstrapper.cc +@@ -1584,6 +1584,50 @@ void Genesis::InitializeGlobal(Handle global_object, + native_context()->set_async_iterator_value_unwrap_shared_fun(*info); + } + ++ { // --- A s y n c G e n e r a t o r --- ++ Handle await_caught = ++ SimpleCreateFunction(isolate, factory->empty_string(), ++ Builtins::kAsyncGeneratorAwaitCaught, 1, false); ++ native_context()->set_async_generator_await_caught(*await_caught); ++ ++ Handle await_uncaught = ++ SimpleCreateFunction(isolate, factory->empty_string(), ++ Builtins::kAsyncGeneratorAwaitUncaught, 1, false); ++ native_context()->set_async_generator_await_uncaught(*await_uncaught); ++ ++ Handle info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncGeneratorAwaitResolveClosure, ++ factory->empty_string(), 1); ++ native_context()->set_async_generator_await_resolve_shared_fun(*info); ++ ++ info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncGeneratorAwaitRejectClosure, ++ factory->empty_string(), 1); ++ native_context()->set_async_generator_await_reject_shared_fun(*info); ++ ++ info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncGeneratorYieldResolveClosure, ++ factory->empty_string(), 1); ++ native_context()->set_async_generator_yield_resolve_shared_fun(*info); ++ ++ info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncGeneratorReturnResolveClosure, ++ factory->empty_string(), 1); ++ native_context()->set_async_generator_return_resolve_shared_fun(*info); ++ ++ info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncGeneratorReturnClosedResolveClosure, ++ factory->empty_string(), 1); ++ native_context()->set_async_generator_return_closed_resolve_shared_fun( ++ *info); ++ ++ info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncGeneratorReturnClosedRejectClosure, ++ factory->empty_string(), 1); ++ native_context()->set_async_generator_return_closed_reject_shared_fun( ++ *info); ++ } ++ + { // --- A r r a y --- + Handle array_function = InstallFunction( + global, "Array", JS_ARRAY_TYPE, JSArray::kSize, 0, +@@ -3998,6 +4042,34 @@ void Bootstrapper::ExportFromRuntime(Isolate* isolate, + JSFunction::SetPrototype(async_function_constructor, + async_function_prototype); + ++ { ++ Handle function = ++ SimpleCreateFunction(isolate, factory->empty_string(), ++ Builtins::kAsyncFunctionAwaitCaught, 2, false); ++ native_context->set_async_function_await_caught(*function); ++ } ++ ++ { ++ Handle function = ++ SimpleCreateFunction(isolate, factory->empty_string(), ++ Builtins::kAsyncFunctionAwaitUncaught, 2, false); ++ native_context->set_async_function_await_uncaught(*function); ++ } ++ ++ { ++ Handle info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncFunctionAwaitRejectClosure, ++ factory->empty_string(), 1); ++ native_context->set_async_function_await_reject_shared_fun(*info); ++ } ++ ++ { ++ Handle info = SimpleCreateSharedFunctionInfo( ++ isolate, Builtins::kAsyncFunctionAwaitResolveClosure, ++ factory->empty_string(), 1); ++ native_context->set_async_function_await_resolve_shared_fun(*info); ++ } ++ + { + Handle function = + SimpleCreateFunction(isolate, factory->empty_string(), +diff --git a/src/builtins/builtins-async-function-gen.cc b/src/builtins/builtins-async-function-gen.cc +index 0db53c687e6..0d0e34ee0da 100644 +--- a/src/builtins/builtins-async-function-gen.cc ++++ b/src/builtins/builtins-async-function-gen.cc +@@ -21,18 +21,37 @@ class AsyncFunctionBuiltinsAssembler : public AsyncBuiltinsAssembler { + Node* const awaited, Node* const outer_promise, + const bool is_predicted_as_caught); + +- void AsyncFunctionAwaitResume(Node* const context, Node* const argument, +- Node* const generator, +- JSGeneratorObject::ResumeMode resume_mode); ++ void AsyncFunctionAwaitResumeClosure( ++ Node* const context, Node* const sent_value, ++ JSGeneratorObject::ResumeMode resume_mode); + }; + +-void AsyncFunctionBuiltinsAssembler::AsyncFunctionAwaitResume( +- Node* const context, Node* const argument, Node* const generator, ++namespace { ++ ++// Describe fields of Context associated with AsyncFunctionAwait resume ++// closures. ++// TODO(jgruber): Refactor to reuse code for upcoming async-generators. ++class AwaitContext { ++ public: ++ enum Fields { kGeneratorSlot = Context::MIN_CONTEXT_SLOTS, kLength }; ++}; ++ ++} // anonymous namespace ++ ++void AsyncFunctionBuiltinsAssembler::AsyncFunctionAwaitResumeClosure( ++ Node* context, Node* sent_value, + JSGeneratorObject::ResumeMode resume_mode) { +- CSA_ASSERT(this, IsJSGeneratorObject(generator)); + DCHECK(resume_mode == JSGeneratorObject::kNext || + resume_mode == JSGeneratorObject::kThrow); + ++ Node* const generator = ++ LoadContextElement(context, AwaitContext::kGeneratorSlot); ++ CSA_SLOW_ASSERT(this, HasInstanceType(generator, JS_GENERATOR_OBJECT_TYPE)); ++ ++ // Inline version of GeneratorPrototypeNext / GeneratorPrototypeReturn with ++ // unnecessary runtime checks removed. ++ // TODO(jgruber): Refactor to reuse code from builtins-generator.cc. ++ + // Ensure that the generator is neither closed nor running. + CSA_SLOW_ASSERT( + this, +@@ -47,23 +66,31 @@ void AsyncFunctionBuiltinsAssembler::AsyncFunctionAwaitResume( + + // Resume the {receiver} using our trampoline. + Callable callable = CodeFactory::ResumeGenerator(isolate()); +- TailCallStub(callable, context, argument, generator); ++ CallStub(callable, context, sent_value, generator); ++ ++ // The resulting Promise is a throwaway, so it doesn't matter what it ++ // resolves to. What is important is that we don't end up keeping the ++ // whole chain of intermediate Promises alive by returning the return value ++ // of ResumeGenerator, as that would create a memory leak. + } + +-TF_BUILTIN(AsyncFunctionAwaitFulfill, AsyncFunctionBuiltinsAssembler) { +- Node* const argument = Parameter(Descriptor::kArgument); +- Node* const generator = Parameter(Descriptor::kGenerator); ++TF_BUILTIN(AsyncFunctionAwaitRejectClosure, AsyncFunctionBuiltinsAssembler) { ++ CSA_ASSERT_JS_ARGC_EQ(this, 1); ++ Node* const sentError = Parameter(Descriptor::kSentError); + Node* const context = Parameter(Descriptor::kContext); +- AsyncFunctionAwaitResume(context, argument, generator, +- JSGeneratorObject::kNext); ++ ++ AsyncFunctionAwaitResumeClosure(context, sentError, ++ JSGeneratorObject::kThrow); ++ Return(UndefinedConstant()); + } + +-TF_BUILTIN(AsyncFunctionAwaitReject, AsyncFunctionBuiltinsAssembler) { +- Node* const argument = Parameter(Descriptor::kArgument); +- Node* const generator = Parameter(Descriptor::kGenerator); ++TF_BUILTIN(AsyncFunctionAwaitResolveClosure, AsyncFunctionBuiltinsAssembler) { ++ CSA_ASSERT_JS_ARGC_EQ(this, 1); ++ Node* const sentValue = Parameter(Descriptor::kSentValue); + Node* const context = Parameter(Descriptor::kContext); +- AsyncFunctionAwaitResume(context, argument, generator, +- JSGeneratorObject::kThrow); ++ ++ AsyncFunctionAwaitResumeClosure(context, sentValue, JSGeneratorObject::kNext); ++ Return(UndefinedConstant()); + } + + // ES#abstract-ops-async-function-await +@@ -78,12 +105,25 @@ TF_BUILTIN(AsyncFunctionAwaitReject, AsyncFunctionBuiltinsAssembler) { + void AsyncFunctionBuiltinsAssembler::AsyncFunctionAwait( + Node* const context, Node* const generator, Node* const awaited, + Node* const outer_promise, const bool is_predicted_as_caught) { +- CSA_SLOW_ASSERT(this, IsJSGeneratorObject(generator)); +- CSA_SLOW_ASSERT(this, IsJSPromise(outer_promise)); +- +- Await(context, generator, awaited, outer_promise, +- Builtins::kAsyncFunctionAwaitFulfill, +- Builtins::kAsyncFunctionAwaitReject, is_predicted_as_caught); ++ CSA_SLOW_ASSERT(this, HasInstanceType(generator, JS_GENERATOR_OBJECT_TYPE)); ++ CSA_SLOW_ASSERT(this, HasInstanceType(outer_promise, JS_PROMISE_TYPE)); ++ ++ ContextInitializer init_closure_context = [&](Node* context) { ++ StoreContextElementNoWriteBarrier(context, AwaitContext::kGeneratorSlot, ++ generator); ++ }; ++ ++ // TODO(jgruber): AsyncBuiltinsAssembler::Await currently does not reuse ++ // the awaited promise if it is already a promise. Reuse is non-spec compliant ++ // but part of our old behavior gives us a couple of percent ++ // performance boost. ++ // TODO(jgruber): Use a faster specialized version of ++ // InternalPerformPromiseThen. ++ ++ Await(context, generator, awaited, outer_promise, AwaitContext::kLength, ++ init_closure_context, Context::ASYNC_FUNCTION_AWAIT_RESOLVE_SHARED_FUN, ++ Context::ASYNC_FUNCTION_AWAIT_REJECT_SHARED_FUN, ++ is_predicted_as_caught); + + // Return outer promise to avoid adding an load of the outer promise before + // suspending in BytecodeGenerator. +@@ -93,28 +133,30 @@ void AsyncFunctionBuiltinsAssembler::AsyncFunctionAwait( + // Called by the parser from the desugaring of 'await' when catch + // prediction indicates that there is a locally surrounding catch block. + TF_BUILTIN(AsyncFunctionAwaitCaught, AsyncFunctionBuiltinsAssembler) { ++ CSA_ASSERT_JS_ARGC_EQ(this, 3); + Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const value = Parameter(Descriptor::kValue); ++ Node* const awaited = Parameter(Descriptor::kAwaited); + Node* const outer_promise = Parameter(Descriptor::kOuterPromise); + Node* const context = Parameter(Descriptor::kContext); + + static const bool kIsPredictedAsCaught = true; + +- AsyncFunctionAwait(context, generator, value, outer_promise, ++ AsyncFunctionAwait(context, generator, awaited, outer_promise, + kIsPredictedAsCaught); + } + + // Called by the parser from the desugaring of 'await' when catch + // prediction indicates no locally surrounding catch block. + TF_BUILTIN(AsyncFunctionAwaitUncaught, AsyncFunctionBuiltinsAssembler) { ++ CSA_ASSERT_JS_ARGC_EQ(this, 3); + Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const value = Parameter(Descriptor::kValue); ++ Node* const awaited = Parameter(Descriptor::kAwaited); + Node* const outer_promise = Parameter(Descriptor::kOuterPromise); + Node* const context = Parameter(Descriptor::kContext); + + static const bool kIsPredictedAsCaught = false; + +- AsyncFunctionAwait(context, generator, value, outer_promise, ++ AsyncFunctionAwait(context, generator, awaited, outer_promise, + kIsPredictedAsCaught); + } + +diff --git a/src/builtins/builtins-async-gen.cc b/src/builtins/builtins-async-gen.cc +index 073c96a2e09..ba0226d7b3a 100644 +--- a/src/builtins/builtins-async-gen.cc ++++ b/src/builtins/builtins-async-gen.cc +@@ -13,58 +13,6 @@ namespace internal { + + using compiler::Node; + +-void AsyncBuiltinsAssembler::Await(Node* context, Node* generator, Node* value, +- Node* outer_promise, +- Builtins::Name fulfill_builtin, +- Builtins::Name reject_builtin, +- Node* is_predicted_as_caught) { +- CSA_SLOW_ASSERT(this, Word32Or(IsJSAsyncGeneratorObject(generator), +- IsJSGeneratorObject(generator))); +- CSA_SLOW_ASSERT(this, IsJSPromise(outer_promise)); +- CSA_SLOW_ASSERT(this, IsBoolean(is_predicted_as_caught)); +- +- Node* const native_context = LoadNativeContext(context); +- +- // TODO(bmeurer): This could be optimized and folded into a single allocation. +- Node* const promise = AllocateAndInitJSPromise(native_context); +- Node* const promise_reactions = +- LoadObjectField(promise, JSPromise::kReactionsOrResultOffset); +- Node* const fulfill_handler = +- HeapConstant(Builtins::CallableFor(isolate(), fulfill_builtin).code()); +- Node* const reject_handler = +- HeapConstant(Builtins::CallableFor(isolate(), reject_builtin).code()); +- Node* const reaction = AllocatePromiseReaction( +- promise_reactions, generator, fulfill_handler, reject_handler); +- StoreObjectField(promise, JSPromise::kReactionsOrResultOffset, reaction); +- PromiseSetHasHandler(promise); +- +- // Perform ! Call(promiseCapability.[[Resolve]], undefined, « value »). +- CallBuiltin(Builtins::kResolvePromise, native_context, promise, value); +- +- // When debugging, we need to link from the {generator} to the +- // {outer_promise} of the async function/generator. +- Label done(this); +- GotoIfNot(IsPromiseHookEnabledOrDebugIsActive(), &done); +- CallRuntime(Runtime::kSetProperty, native_context, generator, +- LoadRoot(Heap::kgenerator_outer_promise_symbolRootIndex), +- outer_promise, SmiConstant(LanguageMode::kStrict)); +- GotoIf(IsFalse(is_predicted_as_caught), &done); +- GotoIf(TaggedIsSmi(value), &done); +- GotoIfNot(IsJSPromise(value), &done); +- PromiseSetHandledHint(value); +- Goto(&done); +- BIND(&done); +-} +- +-void AsyncBuiltinsAssembler::Await(Node* context, Node* generator, Node* value, +- Node* outer_promise, +- Builtins::Name fulfill_builtin, +- Builtins::Name reject_builtin, +- bool is_predicted_as_caught) { +- return Await(context, generator, value, outer_promise, fulfill_builtin, +- reject_builtin, BooleanConstant(is_predicted_as_caught)); +-} +- + namespace { + // Describe fields of Context associated with the AsyncIterator unwrap closure. + class ValueUnwrapContext { +@@ -74,6 +22,161 @@ class ValueUnwrapContext { + + } // namespace + ++Node* AsyncBuiltinsAssembler::Await( ++ Node* context, Node* generator, Node* value, Node* outer_promise, ++ int context_length, const ContextInitializer& init_closure_context, ++ Node* on_resolve_context_index, Node* on_reject_context_index, ++ Node* is_predicted_as_caught) { ++ DCHECK_GE(context_length, Context::MIN_CONTEXT_SLOTS); ++ ++ Node* const native_context = LoadNativeContext(context); ++ ++ static const int kWrappedPromiseOffset = FixedArray::SizeFor(context_length); ++ static const int kThrowawayPromiseOffset = ++ kWrappedPromiseOffset + JSPromise::kSizeWithEmbedderFields; ++ static const int kResolveClosureOffset = ++ kThrowawayPromiseOffset + JSPromise::kSizeWithEmbedderFields; ++ static const int kRejectClosureOffset = ++ kResolveClosureOffset + JSFunction::kSizeWithoutPrototype; ++ static const int kTotalSize = ++ kRejectClosureOffset + JSFunction::kSizeWithoutPrototype; ++ ++ Node* const base = AllocateInNewSpace(kTotalSize); ++ Node* const closure_context = base; ++ { ++ // Initialize closure context ++ InitializeFunctionContext(native_context, closure_context, context_length); ++ init_closure_context(closure_context); ++ } ++ ++ // Let promiseCapability be ! NewPromiseCapability(%Promise%). ++ Node* const promise_fun = ++ LoadContextElement(native_context, Context::PROMISE_FUNCTION_INDEX); ++ CSA_ASSERT(this, IsFunctionWithPrototypeSlotMap(LoadMap(promise_fun))); ++ Node* const promise_map = ++ LoadObjectField(promise_fun, JSFunction::kPrototypeOrInitialMapOffset); ++ // Assert that the JSPromise map has an instance size is ++ // JSPromise::kSizeWithEmbedderFields. ++ CSA_ASSERT(this, WordEqual(LoadMapInstanceSizeInWords(promise_map), ++ IntPtrConstant(JSPromise::kSizeWithEmbedderFields / ++ kPointerSize))); ++ Node* const wrapped_value = InnerAllocate(base, kWrappedPromiseOffset); ++ { ++ // Initialize Promise ++ StoreMapNoWriteBarrier(wrapped_value, promise_map); ++ InitializeJSObjectFromMap( ++ wrapped_value, promise_map, ++ IntPtrConstant(JSPromise::kSizeWithEmbedderFields)); ++ PromiseInit(wrapped_value); ++ } ++ ++ Node* const throwaway = InnerAllocate(base, kThrowawayPromiseOffset); ++ { ++ // Initialize throwawayPromise ++ StoreMapNoWriteBarrier(throwaway, promise_map); ++ InitializeJSObjectFromMap( ++ throwaway, promise_map, ++ IntPtrConstant(JSPromise::kSizeWithEmbedderFields)); ++ PromiseInit(throwaway); ++ } ++ ++ Node* const on_resolve = InnerAllocate(base, kResolveClosureOffset); ++ { ++ // Initialize resolve handler ++ InitializeNativeClosure(closure_context, native_context, on_resolve, ++ on_resolve_context_index); ++ } ++ ++ Node* const on_reject = InnerAllocate(base, kRejectClosureOffset); ++ { ++ // Initialize reject handler ++ InitializeNativeClosure(closure_context, native_context, on_reject, ++ on_reject_context_index); ++ } ++ ++ { ++ // Add PromiseHooks if needed ++ Label next(this); ++ GotoIfNot(IsPromiseHookEnabledOrDebugIsActive(), &next); ++ CallRuntime(Runtime::kPromiseHookInit, context, wrapped_value, ++ outer_promise); ++ CallRuntime(Runtime::kPromiseHookInit, context, throwaway, wrapped_value); ++ Goto(&next); ++ BIND(&next); ++ } ++ ++ // Perform ! Call(promiseCapability.[[Resolve]], undefined, « promise »). ++ CallBuiltin(Builtins::kResolvePromise, context, wrapped_value, value); ++ ++ // The Promise will be thrown away and not handled, but it shouldn't trigger ++ // unhandled reject events as its work is done ++ PromiseSetHasHandler(throwaway); ++ ++ Label do_perform_promise_then(this); ++ GotoIfNot(IsDebugActive(), &do_perform_promise_then); ++ { ++ Label common(this); ++ GotoIf(TaggedIsSmi(value), &common); ++ GotoIfNot(HasInstanceType(value, JS_PROMISE_TYPE), &common); ++ { ++ // Mark the reject handler callback to be a forwarding edge, rather ++ // than a meaningful catch handler ++ Node* const key = ++ HeapConstant(factory()->promise_forwarding_handler_symbol()); ++ CallRuntime(Runtime::kSetProperty, context, on_reject, key, ++ TrueConstant(), SmiConstant(LanguageMode::kStrict)); ++ ++ GotoIf(IsFalse(is_predicted_as_caught), &common); ++ PromiseSetHandledHint(value); ++ } ++ ++ Goto(&common); ++ BIND(&common); ++ // Mark the dependency to outer Promise in case the throwaway Promise is ++ // found on the Promise stack ++ CSA_SLOW_ASSERT(this, HasInstanceType(outer_promise, JS_PROMISE_TYPE)); ++ ++ Node* const key = HeapConstant(factory()->promise_handled_by_symbol()); ++ CallRuntime(Runtime::kSetProperty, context, throwaway, key, outer_promise, ++ SmiConstant(LanguageMode::kStrict)); ++ } ++ ++ Goto(&do_perform_promise_then); ++ BIND(&do_perform_promise_then); ++ return CallBuiltin(Builtins::kPerformPromiseThen, context, wrapped_value, ++ on_resolve, on_reject, throwaway); ++} ++ ++void AsyncBuiltinsAssembler::InitializeNativeClosure(Node* context, ++ Node* native_context, ++ Node* function, ++ Node* context_index) { ++ Node* const function_map = LoadContextElement( ++ native_context, Context::STRICT_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX); ++ // Ensure that we don't have to initialize prototype_or_initial_map field of ++ // JSFunction. ++ CSA_ASSERT(this, WordEqual(LoadMapInstanceSizeInWords(function_map), ++ IntPtrConstant(JSFunction::kSizeWithoutPrototype / ++ kPointerSize))); ++ STATIC_ASSERT(JSFunction::kSizeWithoutPrototype == 7 * kPointerSize); ++ StoreMapNoWriteBarrier(function, function_map); ++ StoreObjectFieldRoot(function, JSObject::kPropertiesOrHashOffset, ++ Heap::kEmptyFixedArrayRootIndex); ++ StoreObjectFieldRoot(function, JSObject::kElementsOffset, ++ Heap::kEmptyFixedArrayRootIndex); ++ StoreObjectFieldRoot(function, JSFunction::kFeedbackCellOffset, ++ Heap::kManyClosuresCellRootIndex); ++ ++ Node* shared_info = LoadContextElement(native_context, context_index); ++ CSA_ASSERT(this, IsSharedFunctionInfo(shared_info)); ++ StoreObjectFieldNoWriteBarrier( ++ function, JSFunction::kSharedFunctionInfoOffset, shared_info); ++ StoreObjectFieldNoWriteBarrier(function, JSFunction::kContextOffset, context); ++ ++ Node* const code = GetSharedFunctionInfoCode(shared_info); ++ StoreObjectFieldNoWriteBarrier(function, JSFunction::kCodeOffset, code); ++} ++ + Node* AsyncBuiltinsAssembler::CreateUnwrapClosure(Node* native_context, + Node* done) { + Node* const map = LoadContextElement( +diff --git a/src/builtins/builtins-async-gen.h b/src/builtins/builtins-async-gen.h +index 70f68a498b7..45d7c8689a9 100644 +--- a/src/builtins/builtins-async-gen.h ++++ b/src/builtins/builtins-async-gen.h +@@ -16,23 +16,48 @@ class AsyncBuiltinsAssembler : public PromiseBuiltinsAssembler { + : PromiseBuiltinsAssembler(state) {} + + protected: +- void Await(Node* context, Node* generator, Node* value, Node* outer_promise, +- Builtins::Name fulfill_builtin, Builtins::Name reject_builtin, +- Node* is_predicted_as_caught); +- void Await(Node* context, Node* generator, Node* value, Node* outer_promise, +- Builtins::Name fulfill_builtin, Builtins::Name reject_builtin, +- bool is_predicted_as_caught); ++ typedef std::function ContextInitializer; ++ ++ // Perform steps to resume generator after `value` is resolved. ++ // `on_reject_context_index` is an index into the Native Context, which should ++ // point to a SharedFunctioninfo instance used to create the closure. The ++ // value following the reject index should be a similar value for the resolve ++ // closure. Returns the Promise-wrapped `value`. ++ Node* Await(Node* context, Node* generator, Node* value, Node* outer_promise, ++ int context_length, ++ const ContextInitializer& init_closure_context, ++ Node* on_resolve_context_index, Node* on_reject_context_index, ++ Node* is_predicted_as_caught); ++ Node* Await(Node* context, Node* generator, Node* value, Node* outer_promise, ++ int context_length, ++ const ContextInitializer& init_closure_context, ++ int on_resolve_context_index, int on_reject_context_index, ++ Node* is_predicted_as_caught) { ++ return Await(context, generator, value, outer_promise, context_length, ++ init_closure_context, IntPtrConstant(on_resolve_context_index), ++ IntPtrConstant(on_reject_context_index), ++ is_predicted_as_caught); ++ } ++ Node* Await(Node* context, Node* generator, Node* value, Node* outer_promise, ++ int context_length, ++ const ContextInitializer& init_closure_context, ++ int on_resolve_context_index, int on_reject_context_index, ++ bool is_predicted_as_caught) { ++ return Await(context, generator, value, outer_promise, context_length, ++ init_closure_context, on_resolve_context_index, ++ on_reject_context_index, ++ BooleanConstant(is_predicted_as_caught)); ++ } + + // Return a new built-in function object as defined in + // Async Iterator Value Unwrap Functions + Node* CreateUnwrapClosure(Node* const native_context, Node* const done); + + private: ++ void InitializeNativeClosure(Node* context, Node* native_context, ++ Node* function, Node* context_index); + Node* AllocateAsyncIteratorValueUnwrapContext(Node* native_context, + Node* done); +- Node* AllocateAwaitPromiseJobTask(Node* generator, Node* fulfill_handler, +- Node* reject_handler, Node* promise, +- Node* context); + }; + + } // namespace internal +diff --git a/src/builtins/builtins-async-generator-gen.cc b/src/builtins/builtins-async-generator-gen.cc +index 290252da624..dd6c6441964 100644 +--- a/src/builtins/builtins-async-generator-gen.cc ++++ b/src/builtins/builtins-async-generator-gen.cc +@@ -140,8 +140,8 @@ class AsyncGeneratorBuiltinsAssembler : public AsyncBuiltinsAssembler { + // for AsyncGenerators. + template + void AsyncGeneratorAwait(bool is_catchable); +- void AsyncGeneratorAwaitResume( +- Node* context, Node* generator, Node* argument, ++ void AsyncGeneratorAwaitResumeClosure( ++ Node* context, Node* value, + JSAsyncGeneratorObject::ResumeMode resume_mode); + }; + +@@ -219,9 +219,11 @@ Node* AsyncGeneratorBuiltinsAssembler::AllocateAsyncGeneratorRequest( + return request; + } + +-void AsyncGeneratorBuiltinsAssembler::AsyncGeneratorAwaitResume( +- Node* context, Node* generator, Node* argument, ++void AsyncGeneratorBuiltinsAssembler::AsyncGeneratorAwaitResumeClosure( ++ Node* context, Node* value, + JSAsyncGeneratorObject::ResumeMode resume_mode) { ++ Node* const generator = ++ LoadContextElement(context, AwaitContext::kGeneratorSlot); + CSA_SLOW_ASSERT(this, TaggedIsAsyncGenerator(generator)); + + SetGeneratorNotAwaiting(generator); +@@ -233,30 +235,36 @@ void AsyncGeneratorBuiltinsAssembler::AsyncGeneratorAwaitResume( + JSGeneratorObject::kResumeModeOffset, + SmiConstant(resume_mode)); + +- CallStub(CodeFactory::ResumeGenerator(isolate()), context, argument, +- generator); ++ CallStub(CodeFactory::ResumeGenerator(isolate()), context, value, generator); + + TailCallBuiltin(Builtins::kAsyncGeneratorResumeNext, context, generator); + } + + template + void AsyncGeneratorBuiltinsAssembler::AsyncGeneratorAwait(bool is_catchable) { +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const value = Parameter(Descriptor::kValue); +- Node* const context = Parameter(Descriptor::kContext); ++ Node* generator = Parameter(Descriptor::kGenerator); ++ Node* value = Parameter(Descriptor::kAwaited); ++ Node* context = Parameter(Descriptor::kContext); + + CSA_SLOW_ASSERT(this, TaggedIsAsyncGenerator(generator)); + + Node* const request = LoadFirstAsyncGeneratorRequestFromQueue(generator); + CSA_ASSERT(this, IsNotUndefined(request)); + ++ ContextInitializer init_closure_context = [&](Node* context) { ++ StoreContextElementNoWriteBarrier(context, AwaitContext::kGeneratorSlot, ++ generator); ++ }; ++ + Node* outer_promise = + LoadObjectField(request, AsyncGeneratorRequest::kPromiseOffset); + ++ const int resolve_index = Context::ASYNC_GENERATOR_AWAIT_RESOLVE_SHARED_FUN; ++ const int reject_index = Context::ASYNC_GENERATOR_AWAIT_REJECT_SHARED_FUN; ++ + SetGeneratorAwaiting(generator); +- Await(context, generator, value, outer_promise, +- Builtins::kAsyncGeneratorAwaitFulfill, +- Builtins::kAsyncGeneratorAwaitReject, is_catchable); ++ Await(context, generator, value, outer_promise, AwaitContext::kLength, ++ init_closure_context, resolve_index, reject_index, is_catchable); + Return(UndefinedConstant()); + } + +@@ -367,20 +375,18 @@ TF_BUILTIN(AsyncGeneratorPrototypeThrow, AsyncGeneratorBuiltinsAssembler) { + "[AsyncGenerator].prototype.throw"); + } + +-TF_BUILTIN(AsyncGeneratorAwaitFulfill, AsyncGeneratorBuiltinsAssembler) { +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const argument = Parameter(Descriptor::kArgument); +- Node* const context = Parameter(Descriptor::kContext); +- AsyncGeneratorAwaitResume(context, generator, argument, +- JSAsyncGeneratorObject::kNext); ++TF_BUILTIN(AsyncGeneratorAwaitResolveClosure, AsyncGeneratorBuiltinsAssembler) { ++ Node* value = Parameter(Descriptor::kValue); ++ Node* context = Parameter(Descriptor::kContext); ++ AsyncGeneratorAwaitResumeClosure(context, value, ++ JSAsyncGeneratorObject::kNext); + } + +-TF_BUILTIN(AsyncGeneratorAwaitReject, AsyncGeneratorBuiltinsAssembler) { +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const argument = Parameter(Descriptor::kArgument); +- Node* const context = Parameter(Descriptor::kContext); +- AsyncGeneratorAwaitResume(context, generator, argument, +- JSAsyncGeneratorObject::kThrow); ++TF_BUILTIN(AsyncGeneratorAwaitRejectClosure, AsyncGeneratorBuiltinsAssembler) { ++ Node* value = Parameter(Descriptor::kValue); ++ Node* context = Parameter(Descriptor::kContext); ++ AsyncGeneratorAwaitResumeClosure(context, value, ++ JSAsyncGeneratorObject::kThrow); + } + + TF_BUILTIN(AsyncGeneratorAwaitUncaught, AsyncGeneratorBuiltinsAssembler) { +@@ -518,34 +524,11 @@ TF_BUILTIN(AsyncGeneratorResolve, AsyncGeneratorBuiltinsAssembler) { + done); + } + +- // We know that {iter_result} itself doesn't have any "then" property and +- // we also know that the [[Prototype]] of {iter_result} is the intrinsic +- // %ObjectPrototype%. So we can skip the [[Resolve]] logic here completely +- // and directly call into the FulfillPromise operation if we can prove +- // that the %ObjectPrototype% also doesn't have any "then" property. This +- // is guarded by the Promise#then protector. +- Label if_fast(this), if_slow(this, Label::kDeferred), return_promise(this); +- GotoIfForceSlowPath(&if_slow); +- Branch(IsPromiseThenProtectorCellInvalid(), &if_slow, &if_fast); +- +- BIND(&if_fast); +- { +- // Skip the "then" on {iter_result} and directly fulfill the {promise} +- // with the {iter_result}. +- CallBuiltin(Builtins::kFulfillPromise, context, promise, iter_result); +- Goto(&return_promise); +- } +- +- BIND(&if_slow); +- { +- // Perform Call(promiseCapability.[[Resolve]], undefined, «iteratorResult»). +- CallBuiltin(Builtins::kResolvePromise, context, promise, iter_result); +- Goto(&return_promise); +- } ++ // Perform Call(promiseCapability.[[Resolve]], undefined, «iteratorResult»). ++ CallBuiltin(Builtins::kResolvePromise, context, promise, iter_result); + + // Per spec, AsyncGeneratorResolve() returns undefined. However, for the + // benefit of %TraceExit(), return the Promise. +- BIND(&return_promise); + Return(promise); + } + +@@ -571,54 +554,31 @@ TF_BUILTIN(AsyncGeneratorYield, AsyncGeneratorBuiltinsAssembler) { + Node* const request = LoadFirstAsyncGeneratorRequestFromQueue(generator); + Node* const outer_promise = LoadPromiseFromAsyncGeneratorRequest(request); + +- // Mark the generator as "awaiting". +- SetGeneratorAwaiting(generator); ++ ContextInitializer init_closure_context = [&](Node* context) { ++ StoreContextElementNoWriteBarrier(context, AwaitContext::kGeneratorSlot, ++ generator); ++ }; + +- // We can skip the creation of a temporary promise and the whole +- // [[Resolve]] logic if we already know that the {value} that's +- // being yielded is a primitive, as in that case we would immediately +- // fulfill the temporary promise anyways and schedule a fulfill +- // reaction job. This gives a nice performance boost for async +- // generators that yield only primitives, e.g. numbers or strings. +- Label if_primitive(this), if_generic(this); +- GotoIfForceSlowPath(&if_generic); +- GotoIf(IsPromiseHookEnabledOrDebugIsActive(), &if_generic); +- GotoIf(TaggedIsSmi(value), &if_primitive); +- Branch(IsJSReceiver(value), &if_generic, &if_primitive); +- +- BIND(&if_generic); +- { +- Await(context, generator, value, outer_promise, +- Builtins::kAsyncGeneratorYieldFulfill, +- Builtins::kAsyncGeneratorAwaitReject, is_caught); +- Return(UndefinedConstant()); +- } ++ const int on_resolve = Context::ASYNC_GENERATOR_YIELD_RESOLVE_SHARED_FUN; ++ const int on_reject = Context::ASYNC_GENERATOR_AWAIT_REJECT_SHARED_FUN; + +- BIND(&if_primitive); +- { +- // For primitive {value}s we can skip the allocation of the temporary +- // promise and the resolution of that, and directly allocate the fulfill +- // reaction job. +- Node* const microtask = AllocatePromiseReactionJobTask( +- Heap::kPromiseFulfillReactionJobTaskMapRootIndex, context, value, +- HeapConstant(Builtins::CallableFor( +- isolate(), Builtins::kAsyncGeneratorYieldFulfill) +- .code()), +- generator); +- TailCallBuiltin(Builtins::kEnqueueMicrotask, context, microtask); +- } ++ SetGeneratorAwaiting(generator); ++ Await(context, generator, value, outer_promise, AwaitContext::kLength, ++ init_closure_context, on_resolve, on_reject, is_caught); ++ Return(UndefinedConstant()); + } + +-TF_BUILTIN(AsyncGeneratorYieldFulfill, AsyncGeneratorBuiltinsAssembler) { ++TF_BUILTIN(AsyncGeneratorYieldResolveClosure, AsyncGeneratorBuiltinsAssembler) { + Node* const context = Parameter(Descriptor::kContext); +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const argument = Parameter(Descriptor::kArgument); ++ Node* const value = Parameter(Descriptor::kValue); ++ Node* const generator = ++ LoadContextElement(context, AwaitContext::kGeneratorSlot); + + SetGeneratorNotAwaiting(generator); + + // Per proposal-async-iteration/#sec-asyncgeneratoryield step 9 + // Return ! AsyncGeneratorResolve(_F_.[[Generator]], _value_, *false*). +- CallBuiltin(Builtins::kAsyncGeneratorResolve, context, generator, argument, ++ CallBuiltin(Builtins::kAsyncGeneratorResolve, context, generator, value, + FalseConstant()); + + TailCallBuiltin(Builtins::kAsyncGeneratorResumeNext, context, generator); +@@ -644,33 +604,39 @@ TF_BUILTIN(AsyncGeneratorReturn, AsyncGeneratorBuiltinsAssembler) { + Node* const generator = Parameter(Descriptor::kGenerator); + Node* const value = Parameter(Descriptor::kValue); + Node* const is_caught = Parameter(Descriptor::kIsCaught); +- Node* const context = Parameter(Descriptor::kContext); + Node* const req = LoadFirstAsyncGeneratorRequestFromQueue(generator); +- Node* const outer_promise = LoadPromiseFromAsyncGeneratorRequest(req); + CSA_ASSERT(this, IsNotUndefined(req)); + +- Label if_closed(this, Label::kDeferred), if_not_closed(this), done(this); ++ Label perform_await(this); ++ VARIABLE(var_on_resolve, MachineType::PointerRepresentation(), ++ IntPtrConstant( ++ Context::ASYNC_GENERATOR_RETURN_CLOSED_RESOLVE_SHARED_FUN)); ++ VARIABLE( ++ var_on_reject, MachineType::PointerRepresentation(), ++ IntPtrConstant(Context::ASYNC_GENERATOR_RETURN_CLOSED_REJECT_SHARED_FUN)); ++ + Node* const state = LoadGeneratorState(generator); +- SetGeneratorAwaiting(generator); +- Branch(IsGeneratorStateClosed(state), &if_closed, &if_not_closed); ++ GotoIf(IsGeneratorStateClosed(state), &perform_await); ++ var_on_resolve.Bind( ++ IntPtrConstant(Context::ASYNC_GENERATOR_RETURN_RESOLVE_SHARED_FUN)); ++ var_on_reject.Bind( ++ IntPtrConstant(Context::ASYNC_GENERATOR_AWAIT_REJECT_SHARED_FUN)); ++ Goto(&perform_await); + +- BIND(&if_closed); +- { +- Await(context, generator, value, outer_promise, +- Builtins::kAsyncGeneratorReturnClosedFulfill, +- Builtins::kAsyncGeneratorReturnClosedReject, is_caught); +- Goto(&done); +- } ++ BIND(&perform_await); + +- BIND(&if_not_closed); +- { +- Await(context, generator, value, outer_promise, +- Builtins::kAsyncGeneratorReturnFulfill, +- Builtins::kAsyncGeneratorAwaitReject, is_caught); +- Goto(&done); +- } ++ ContextInitializer init_closure_context = [&](Node* context) { ++ StoreContextElementNoWriteBarrier(context, AwaitContext::kGeneratorSlot, ++ generator); ++ }; ++ ++ SetGeneratorAwaiting(generator); ++ Node* const context = Parameter(Descriptor::kContext); ++ Node* const outer_promise = LoadPromiseFromAsyncGeneratorRequest(req); ++ Await(context, generator, value, outer_promise, AwaitContext::kLength, ++ init_closure_context, var_on_resolve.value(), var_on_reject.value(), ++ is_caught); + +- BIND(&done); + Return(UndefinedConstant()); + } + +@@ -678,44 +644,47 @@ TF_BUILTIN(AsyncGeneratorReturn, AsyncGeneratorBuiltinsAssembler) { + // Resume the generator with "return" resume_mode, and finally perform + // AsyncGeneratorResumeNext. Per + // proposal-async-iteration/#sec-asyncgeneratoryield step 8.e +-TF_BUILTIN(AsyncGeneratorReturnFulfill, AsyncGeneratorBuiltinsAssembler) { +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const argument = Parameter(Descriptor::kArgument); ++TF_BUILTIN(AsyncGeneratorReturnResolveClosure, ++ AsyncGeneratorBuiltinsAssembler) { + Node* const context = Parameter(Descriptor::kContext); +- AsyncGeneratorAwaitResume(context, generator, argument, +- JSGeneratorObject::kReturn); ++ Node* const value = Parameter(Descriptor::kValue); ++ AsyncGeneratorAwaitResumeClosure(context, value, JSGeneratorObject::kReturn); + } + + // On-resolve closure for Await in AsyncGeneratorReturn + // Perform AsyncGeneratorResolve({awaited_value}, true) and finally perform + // AsyncGeneratorResumeNext. +-TF_BUILTIN(AsyncGeneratorReturnClosedFulfill, AsyncGeneratorBuiltinsAssembler) { +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const argument = Parameter(Descriptor::kArgument); ++TF_BUILTIN(AsyncGeneratorReturnClosedResolveClosure, ++ AsyncGeneratorBuiltinsAssembler) { + Node* const context = Parameter(Descriptor::kContext); ++ Node* const value = Parameter(Descriptor::kValue); ++ Node* const generator = ++ LoadContextElement(context, AwaitContext::kGeneratorSlot); + + SetGeneratorNotAwaiting(generator); + + // https://tc39.github.io/proposal-async-iteration/ + // #async-generator-resume-next-return-processor-fulfilled step 2: + // Return ! AsyncGeneratorResolve(_F_.[[Generator]], _value_, *true*). +- CallBuiltin(Builtins::kAsyncGeneratorResolve, context, generator, argument, ++ CallBuiltin(Builtins::kAsyncGeneratorResolve, context, generator, value, + TrueConstant()); + + TailCallBuiltin(Builtins::kAsyncGeneratorResumeNext, context, generator); + } + +-TF_BUILTIN(AsyncGeneratorReturnClosedReject, AsyncGeneratorBuiltinsAssembler) { +- Node* const generator = Parameter(Descriptor::kGenerator); +- Node* const argument = Parameter(Descriptor::kArgument); ++TF_BUILTIN(AsyncGeneratorReturnClosedRejectClosure, ++ AsyncGeneratorBuiltinsAssembler) { + Node* const context = Parameter(Descriptor::kContext); ++ Node* const value = Parameter(Descriptor::kValue); ++ Node* const generator = ++ LoadContextElement(context, AwaitContext::kGeneratorSlot); + + SetGeneratorNotAwaiting(generator); + + // https://tc39.github.io/proposal-async-iteration/ + // #async-generator-resume-next-return-processor-rejected step 2: + // Return ! AsyncGeneratorReject(_F_.[[Generator]], _reason_). +- CallBuiltin(Builtins::kAsyncGeneratorReject, context, generator, argument); ++ CallBuiltin(Builtins::kAsyncGeneratorReject, context, generator, value); + + TailCallBuiltin(Builtins::kAsyncGeneratorResumeNext, context, generator); + } +diff --git a/src/builtins/builtins-definitions.h b/src/builtins/builtins-definitions.h +index 0f60dfd97e8..5f06abeceb0 100644 +--- a/src/builtins/builtins-definitions.h ++++ b/src/builtins/builtins-definitions.h +@@ -381,10 +381,10 @@ namespace internal { + CPP(ArrayBufferPrototypeSlice) \ + \ + /* AsyncFunction */ \ +- TFC(AsyncFunctionAwaitFulfill, PromiseReactionHandler, 1) \ +- TFC(AsyncFunctionAwaitReject, PromiseReactionHandler, 1) \ +- TFS(AsyncFunctionAwaitCaught, kGenerator, kValue, kOuterPromise) \ +- TFS(AsyncFunctionAwaitUncaught, kGenerator, kValue, kOuterPromise) \ ++ TFJ(AsyncFunctionAwaitCaught, 3, kGenerator, kAwaited, kOuterPromise) \ ++ TFJ(AsyncFunctionAwaitUncaught, 3, kGenerator, kAwaited, kOuterPromise) \ ++ TFJ(AsyncFunctionAwaitRejectClosure, 1, kSentError) \ ++ TFJ(AsyncFunctionAwaitResolveClosure, 1, kSentValue) \ + TFJ(AsyncFunctionPromiseCreate, 0) \ + TFJ(AsyncFunctionPromiseRelease, 1, kPromise) \ + \ +@@ -838,8 +838,8 @@ namespace internal { + /* ES #sec-promise.prototype.catch */ \ + TFJ(PromisePrototypeCatch, 1, kOnRejected) \ + /* ES #sec-promisereactionjob */ \ +- TFS(PromiseRejectReactionJob, kReason, kHandler, kPayload) \ +- TFS(PromiseFulfillReactionJob, kValue, kHandler, kPayload) \ ++ TFS(PromiseRejectReactionJob, kReason, kHandler, kPromiseOrCapability) \ ++ TFS(PromiseFulfillReactionJob, kValue, kHandler, kPromiseOrCapability) \ + /* ES #sec-promiseresolvethenablejob */ \ + TFS(PromiseResolveThenableJob, kPromiseToResolve, kThenable, kThen) \ + /* ES #sec-promise.resolve */ \ +@@ -1203,17 +1203,6 @@ namespace internal { + \ + /* AsyncGenerator */ \ + \ +- /* Await (proposal-async-iteration/#await), with resume behaviour */ \ +- /* specific to Async Generators. Internal / Not exposed to JS code. */ \ +- TFS(AsyncGeneratorAwaitCaught, kGenerator, kValue) \ +- TFS(AsyncGeneratorAwaitUncaught, kGenerator, kValue) \ +- TFC(AsyncGeneratorAwaitFulfill, PromiseReactionHandler, 1) \ +- TFC(AsyncGeneratorAwaitReject, PromiseReactionHandler, 1) \ +- TFC(AsyncGeneratorYieldFulfill, PromiseReactionHandler, 1) \ +- TFC(AsyncGeneratorReturnClosedFulfill, PromiseReactionHandler, 1) \ +- TFC(AsyncGeneratorReturnClosedReject, PromiseReactionHandler, 1) \ +- TFC(AsyncGeneratorReturnFulfill, PromiseReactionHandler, 1) \ +- \ + TFS(AsyncGeneratorResolve, kGenerator, kValue, kDone) \ + TFS(AsyncGeneratorReject, kGenerator, kValue) \ + TFS(AsyncGeneratorYield, kGenerator, kValue, kIsCaught) \ +@@ -1236,6 +1225,17 @@ namespace internal { + TFJ(AsyncGeneratorPrototypeThrow, \ + SharedFunctionInfo::kDontAdaptArgumentsSentinel) \ + \ ++ /* Await (proposal-async-iteration/#await), with resume behaviour */ \ ++ /* specific to Async Generators. Internal / Not exposed to JS code. */ \ ++ TFJ(AsyncGeneratorAwaitCaught, 2, kGenerator, kAwaited) \ ++ TFJ(AsyncGeneratorAwaitUncaught, 2, kGenerator, kAwaited) \ ++ TFJ(AsyncGeneratorAwaitResolveClosure, 1, kValue) \ ++ TFJ(AsyncGeneratorAwaitRejectClosure, 1, kValue) \ ++ TFJ(AsyncGeneratorYieldResolveClosure, 1, kValue) \ ++ TFJ(AsyncGeneratorReturnClosedResolveClosure, 1, kValue) \ ++ TFJ(AsyncGeneratorReturnClosedRejectClosure, 1, kValue) \ ++ TFJ(AsyncGeneratorReturnResolveClosure, 1, kValue) \ ++ \ + /* Async-from-Sync Iterator */ \ + \ + /* %AsyncFromSyncIteratorPrototype% */ \ +@@ -1284,7 +1284,11 @@ namespace internal { + V(AsyncFromSyncIteratorPrototypeNext) \ + V(AsyncFromSyncIteratorPrototypeReturn) \ + V(AsyncFromSyncIteratorPrototypeThrow) \ ++ V(AsyncFunctionAwaitCaught) \ ++ V(AsyncFunctionAwaitUncaught) \ + V(AsyncGeneratorResolve) \ ++ V(AsyncGeneratorAwaitCaught) \ ++ V(AsyncGeneratorAwaitUncaught) \ + V(PromiseAll) \ + V(PromiseConstructor) \ + V(PromiseConstructorLazyDeoptContinuation) \ +diff --git a/src/builtins/builtins-internal-gen.cc b/src/builtins/builtins-internal-gen.cc +index e1f4aea4052..4e533ad1c4c 100644 +--- a/src/builtins/builtins-internal-gen.cc ++++ b/src/builtins/builtins-internal-gen.cc +@@ -669,7 +669,7 @@ class InternalBuiltinsAssembler : public CodeStubAssembler { + void LeaveMicrotaskContext(); + + void RunPromiseHook(Runtime::FunctionId id, TNode context, +- SloppyTNode payload); ++ SloppyTNode promise_or_capability); + + TNode GetPendingException() { + auto ref = ExternalReference(kPendingExceptionAddress, isolate()); +@@ -790,12 +790,20 @@ void InternalBuiltinsAssembler::LeaveMicrotaskContext() { + + void InternalBuiltinsAssembler::RunPromiseHook( + Runtime::FunctionId id, TNode context, +- SloppyTNode payload) { ++ SloppyTNode promise_or_capability) { + Label hook(this, Label::kDeferred), done_hook(this); + Branch(IsPromiseHookEnabledOrDebugIsActive(), &hook, &done_hook); + BIND(&hook); + { +- CallRuntime(id, context, payload); ++ // Get to the underlying JSPromise instance. ++ Node* const promise = Select( ++ IsJSPromise(promise_or_capability), ++ [=] { return promise_or_capability; }, ++ [=] { ++ return CAST(LoadObjectField(promise_or_capability, ++ PromiseCapability::kPromiseOffset)); ++ }); ++ CallRuntime(id, context, promise); + Goto(&done_hook); + } + BIND(&done_hook); +@@ -1008,19 +1016,21 @@ TF_BUILTIN(RunMicrotasks, InternalBuiltinsAssembler) { + LoadObjectField(microtask, PromiseReactionJobTask::kArgumentOffset); + Node* const handler = + LoadObjectField(microtask, PromiseReactionJobTask::kHandlerOffset); +- Node* const payload = +- LoadObjectField(microtask, PromiseReactionJobTask::kPayloadOffset); ++ Node* const promise_or_capability = LoadObjectField( ++ microtask, PromiseReactionJobTask::kPromiseOrCapabilityOffset); + + // Run the promise before/debug hook if enabled. +- RunPromiseHook(Runtime::kPromiseHookBefore, microtask_context, payload); ++ RunPromiseHook(Runtime::kPromiseHookBefore, microtask_context, ++ promise_or_capability); + + Node* const result = + CallBuiltin(Builtins::kPromiseFulfillReactionJob, microtask_context, +- argument, handler, payload); ++ argument, handler, promise_or_capability); + GotoIfException(result, &if_exception, &var_exception); + + // Run the promise after/debug hook if enabled. +- RunPromiseHook(Runtime::kPromiseHookAfter, microtask_context, payload); ++ RunPromiseHook(Runtime::kPromiseHookAfter, microtask_context, ++ promise_or_capability); + + LeaveMicrotaskContext(); + SetCurrentContext(current_context); +@@ -1041,19 +1051,21 @@ TF_BUILTIN(RunMicrotasks, InternalBuiltinsAssembler) { + LoadObjectField(microtask, PromiseReactionJobTask::kArgumentOffset); + Node* const handler = + LoadObjectField(microtask, PromiseReactionJobTask::kHandlerOffset); +- Node* const payload = +- LoadObjectField(microtask, PromiseReactionJobTask::kPayloadOffset); ++ Node* const promise_or_capability = LoadObjectField( ++ microtask, PromiseReactionJobTask::kPromiseOrCapabilityOffset); + + // Run the promise before/debug hook if enabled. +- RunPromiseHook(Runtime::kPromiseHookBefore, microtask_context, payload); ++ RunPromiseHook(Runtime::kPromiseHookBefore, microtask_context, ++ promise_or_capability); + + Node* const result = + CallBuiltin(Builtins::kPromiseRejectReactionJob, microtask_context, +- argument, handler, payload); ++ argument, handler, promise_or_capability); + GotoIfException(result, &if_exception, &var_exception); + + // Run the promise after/debug hook if enabled. +- RunPromiseHook(Runtime::kPromiseHookAfter, microtask_context, payload); ++ RunPromiseHook(Runtime::kPromiseHookAfter, microtask_context, ++ promise_or_capability); + + LeaveMicrotaskContext(); + SetCurrentContext(current_context); +diff --git a/src/builtins/builtins-promise-gen.cc b/src/builtins/builtins-promise-gen.cc +index dd38dbc5435..868b45a8316 100644 +--- a/src/builtins/builtins-promise-gen.cc ++++ b/src/builtins/builtins-promise-gen.cc +@@ -391,15 +391,15 @@ TF_BUILTIN(PerformPromiseThen, PromiseBuiltinsAssembler) { + Return(result_promise); + } + +-Node* PromiseBuiltinsAssembler::AllocatePromiseReaction(Node* next, +- Node* payload, +- Node* fulfill_handler, +- Node* reject_handler) { ++Node* PromiseBuiltinsAssembler::AllocatePromiseReaction( ++ Node* next, Node* promise_or_capability, Node* fulfill_handler, ++ Node* reject_handler) { + Node* const reaction = Allocate(PromiseReaction::kSize); + StoreMapNoWriteBarrier(reaction, Heap::kPromiseReactionMapRootIndex); + StoreObjectFieldNoWriteBarrier(reaction, PromiseReaction::kNextOffset, next); +- StoreObjectFieldNoWriteBarrier(reaction, PromiseReaction::kPayloadOffset, +- payload); ++ StoreObjectFieldNoWriteBarrier(reaction, ++ PromiseReaction::kPromiseOrCapabilityOffset, ++ promise_or_capability); + StoreObjectFieldNoWriteBarrier( + reaction, PromiseReaction::kFulfillHandlerOffset, fulfill_handler); + StoreObjectFieldNoWriteBarrier( +@@ -408,7 +408,8 @@ Node* PromiseBuiltinsAssembler::AllocatePromiseReaction(Node* next, + } + + Node* PromiseBuiltinsAssembler::AllocatePromiseReactionJobTask( +- Node* map, Node* context, Node* argument, Node* handler, Node* payload) { ++ Node* map, Node* context, Node* argument, Node* handler, ++ Node* promise_or_capability) { + Node* const microtask = Allocate(PromiseReactionJobTask::kSize); + StoreMapNoWriteBarrier(microtask, map); + StoreObjectFieldNoWriteBarrier( +@@ -418,18 +419,19 @@ Node* PromiseBuiltinsAssembler::AllocatePromiseReactionJobTask( + StoreObjectFieldNoWriteBarrier( + microtask, PromiseReactionJobTask::kHandlerOffset, handler); + StoreObjectFieldNoWriteBarrier( +- microtask, PromiseReactionJobTask::kPayloadOffset, payload); ++ microtask, PromiseReactionJobTask::kPromiseOrCapabilityOffset, ++ promise_or_capability); + return microtask; + } + + Node* PromiseBuiltinsAssembler::AllocatePromiseReactionJobTask( + Heap::RootListIndex map_root_index, Node* context, Node* argument, +- Node* handler, Node* payload) { ++ Node* handler, Node* promise_or_capability) { + DCHECK(map_root_index == Heap::kPromiseFulfillReactionJobTaskMapRootIndex || + map_root_index == Heap::kPromiseRejectReactionJobTaskMapRootIndex); + Node* const map = LoadRoot(map_root_index); + return AllocatePromiseReactionJobTask(map, context, argument, handler, +- payload); ++ promise_or_capability); + } + + Node* PromiseBuiltinsAssembler::AllocatePromiseResolveThenableJobTask( +@@ -502,8 +504,8 @@ Node* PromiseBuiltinsAssembler::TriggerPromiseReactions( + context); + STATIC_ASSERT(PromiseReaction::kFulfillHandlerOffset == + PromiseReactionJobTask::kHandlerOffset); +- STATIC_ASSERT(PromiseReaction::kPayloadOffset == +- PromiseReactionJobTask::kPayloadOffset); ++ STATIC_ASSERT(PromiseReaction::kPromiseOrCapabilityOffset == ++ PromiseReactionJobTask::kPromiseOrCapabilityOffset); + } else { + Node* handler = + LoadObjectField(current, PromiseReaction::kRejectHandlerOffset); +@@ -515,8 +517,8 @@ Node* PromiseBuiltinsAssembler::TriggerPromiseReactions( + context); + StoreObjectField(current, PromiseReactionJobTask::kHandlerOffset, + handler); +- STATIC_ASSERT(PromiseReaction::kPayloadOffset == +- PromiseReactionJobTask::kPayloadOffset); ++ STATIC_ASSERT(PromiseReaction::kPromiseOrCapabilityOffset == ++ PromiseReactionJobTask::kPromiseOrCapabilityOffset); + } + CallBuiltin(Builtins::kEnqueueMicrotask, NoContextConstant(), current); + Goto(&loop); +@@ -1118,28 +1120,20 @@ TF_BUILTIN(PromiseResolveThenableJob, PromiseBuiltinsAssembler) { + + // ES #sec-promisereactionjob + void PromiseBuiltinsAssembler::PromiseReactionJob(Node* context, Node* argument, +- Node* handler, Node* payload, ++ Node* handler, ++ Node* promise_or_capability, + PromiseReaction::Type type) { + CSA_ASSERT(this, TaggedIsNotSmi(handler)); +- CSA_ASSERT(this, Word32Or(IsCallable(handler), +- Word32Or(IsCode(handler), IsUndefined(handler)))); +- CSA_ASSERT(this, TaggedIsNotSmi(payload)); ++ CSA_ASSERT(this, Word32Or(IsUndefined(handler), IsCallable(handler))); ++ CSA_ASSERT(this, TaggedIsNotSmi(promise_or_capability)); ++ CSA_ASSERT(this, Word32Or(IsJSPromise(promise_or_capability), ++ IsPromiseCapability(promise_or_capability))); + + VARIABLE(var_handler_result, MachineRepresentation::kTagged, argument); +- Label if_handler_callable(this), if_fulfill(this), if_reject(this), +- if_code_handler(this); +- +- GotoIf(IsUndefined(handler), +- type == PromiseReaction::kFulfill ? &if_fulfill : &if_reject); +- Branch(IsCode(handler), &if_code_handler, &if_handler_callable); +- +- BIND(&if_code_handler); +- { +- // The {handler} is a Code object that knows how to deal with +- // the {payload} and the {argument}. +- PromiseReactionHandlerDescriptor descriptor(isolate()); +- TailCallStub(descriptor, handler, context, argument, payload); +- } ++ Label if_handler_callable(this), if_fulfill(this), if_reject(this); ++ Branch(IsUndefined(handler), ++ type == PromiseReaction::kFulfill ? &if_fulfill : &if_reject, ++ &if_handler_callable); + + BIND(&if_handler_callable); + { +@@ -1155,22 +1149,24 @@ void PromiseBuiltinsAssembler::PromiseReactionJob(Node* context, Node* argument, + { + Label if_promise(this), if_promise_capability(this, Label::kDeferred); + Node* const value = var_handler_result.value(); +- Branch(IsPromiseCapability(payload), &if_promise_capability, &if_promise); ++ Branch(IsPromiseCapability(promise_or_capability), &if_promise_capability, ++ &if_promise); + + BIND(&if_promise); + { + // For fast native promises we can skip the indirection + // via the promiseCapability.[[Resolve]] function and + // run the resolve logic directly from here. +- TailCallBuiltin(Builtins::kResolvePromise, context, payload, value); ++ TailCallBuiltin(Builtins::kResolvePromise, context, promise_or_capability, ++ value); + } + + BIND(&if_promise_capability); + { + // In the general case we need to call the (user provided) + // promiseCapability.[[Resolve]] function. +- Node* const resolve = +- LoadObjectField(payload, PromiseCapability::kResolveOffset); ++ Node* const resolve = LoadObjectField(promise_or_capability, ++ PromiseCapability::kResolveOffset); + Node* const result = CallJS( + CodeFactory::Call(isolate(), ConvertReceiverMode::kNullOrUndefined), + context, resolve, UndefinedConstant(), value); +@@ -1183,15 +1179,16 @@ void PromiseBuiltinsAssembler::PromiseReactionJob(Node* context, Node* argument, + if (type == PromiseReaction::kReject) { + Label if_promise(this), if_promise_capability(this, Label::kDeferred); + Node* const reason = var_handler_result.value(); +- Branch(IsPromiseCapability(payload), &if_promise_capability, &if_promise); ++ Branch(IsPromiseCapability(promise_or_capability), &if_promise_capability, ++ &if_promise); + + BIND(&if_promise); + { + // For fast native promises we can skip the indirection + // via the promiseCapability.[[Reject]] function and + // run the resolve logic directly from here. +- TailCallBuiltin(Builtins::kRejectPromise, context, payload, reason, +- FalseConstant()); ++ TailCallBuiltin(Builtins::kRejectPromise, context, promise_or_capability, ++ reason, FalseConstant()); + } + + BIND(&if_promise_capability); +@@ -1201,8 +1198,8 @@ void PromiseBuiltinsAssembler::PromiseReactionJob(Node* context, Node* argument, + Label if_exception(this, Label::kDeferred); + VARIABLE(var_exception, MachineRepresentation::kTagged, + TheHoleConstant()); +- Node* const reject = +- LoadObjectField(payload, PromiseCapability::kRejectOffset); ++ Node* const reject = LoadObjectField(promise_or_capability, ++ PromiseCapability::kRejectOffset); + Node* const result = CallJS( + CodeFactory::Call(isolate(), ConvertReceiverMode::kNullOrUndefined), + context, reject, UndefinedConstant(), reason); +@@ -1219,7 +1216,8 @@ void PromiseBuiltinsAssembler::PromiseReactionJob(Node* context, Node* argument, + // predictions in the debugger will be wrong, which just walks the stack + // and checks for certain builtins. + TailCallBuiltin(Builtins::kPromiseRejectReactionJob, context, +- var_handler_result.value(), UndefinedConstant(), payload); ++ var_handler_result.value(), UndefinedConstant(), ++ promise_or_capability); + } + } + +@@ -1228,9 +1226,10 @@ TF_BUILTIN(PromiseFulfillReactionJob, PromiseBuiltinsAssembler) { + Node* const context = Parameter(Descriptor::kContext); + Node* const value = Parameter(Descriptor::kValue); + Node* const handler = Parameter(Descriptor::kHandler); +- Node* const payload = Parameter(Descriptor::kPayload); ++ Node* const promise_or_capability = ++ Parameter(Descriptor::kPromiseOrCapability); + +- PromiseReactionJob(context, value, handler, payload, ++ PromiseReactionJob(context, value, handler, promise_or_capability, + PromiseReaction::kFulfill); + } + +@@ -1239,9 +1238,10 @@ TF_BUILTIN(PromiseRejectReactionJob, PromiseBuiltinsAssembler) { + Node* const context = Parameter(Descriptor::kContext); + Node* const reason = Parameter(Descriptor::kReason); + Node* const handler = Parameter(Descriptor::kHandler); +- Node* const payload = Parameter(Descriptor::kPayload); ++ Node* const promise_or_capability = ++ Parameter(Descriptor::kPromiseOrCapability); + +- PromiseReactionJob(context, reason, handler, payload, ++ PromiseReactionJob(context, reason, handler, promise_or_capability, + PromiseReaction::kReject); + } + +@@ -1717,23 +1717,21 @@ TF_BUILTIN(ResolvePromise, PromiseBuiltinsAssembler) { + + // 7. If Type(resolution) is not Object, then + GotoIf(TaggedIsSmi(resolution), &if_fulfill); +- Node* const resolution_map = LoadMap(resolution); +- GotoIfNot(IsJSReceiverMap(resolution_map), &if_fulfill); ++ Node* const result_map = LoadMap(resolution); ++ GotoIfNot(IsJSReceiverMap(result_map), &if_fulfill); + + // We can skip the "then" lookup on {resolution} if its [[Prototype]] + // is the (initial) Promise.prototype and the Promise#then protector + // is intact, as that guards the lookup path for the "then" property + // on JSPromise instances which have the (initial) %PromisePrototype%. +- Label if_fast(this), if_generic(this), if_slow(this, Label::kDeferred); ++ Label if_fast(this), if_slow(this, Label::kDeferred); + Node* const native_context = LoadNativeContext(context); +- GotoIfForceSlowPath(&if_slow); +- GotoIf(IsPromiseThenProtectorCellInvalid(), &if_slow); +- GotoIfNot(IsJSPromiseMap(resolution_map), &if_generic); +- Node* const promise_prototype = +- LoadContextElement(native_context, Context::PROMISE_PROTOTYPE_INDEX); +- Branch(WordEqual(LoadMapPrototype(resolution_map), promise_prototype), +- &if_fast, &if_slow); ++ BranchIfPromiseThenLookupChainIntact(native_context, result_map, &if_fast, ++ &if_slow); + ++ // Resolution is a native promise and if it's already resolved or ++ // rejected, shortcircuit the resolution procedure by directly ++ // reusing the value from the promise. + BIND(&if_fast); + { + Node* const then = +@@ -1742,21 +1740,6 @@ TF_BUILTIN(ResolvePromise, PromiseBuiltinsAssembler) { + Goto(&do_enqueue); + } + +- BIND(&if_generic); +- { +- // We can skip the lookup of "then" if the {resolution} is a (newly +- // created) IterResultObject, as the Promise#then protector also +- // ensures that the intrinsic %ObjectPrototype% doesn't contain any +- // "then" property. This helps to avoid negative lookups on iterator +- // results from async generators. +- CSA_ASSERT(this, IsJSReceiverMap(resolution_map)); +- CSA_ASSERT(this, Word32BinaryNot(IsPromiseThenProtectorCellInvalid())); +- Node* const iterator_result_map = +- LoadContextElement(native_context, Context::ITERATOR_RESULT_MAP_INDEX); +- Branch(WordEqual(resolution_map, iterator_result_map), &if_fulfill, +- &if_slow); +- } +- + BIND(&if_slow); + { + // 8. Let then be Get(resolution, "then"). +diff --git a/src/builtins/builtins-promise-gen.h b/src/builtins/builtins-promise-gen.h +index f21d86a141a..694cea28c06 100644 +--- a/src/builtins/builtins-promise-gen.h ++++ b/src/builtins/builtins-promise-gen.h +@@ -85,14 +85,16 @@ class PromiseBuiltinsAssembler : public CodeStubAssembler { + Node* AllocateAndSetJSPromise(Node* context, v8::Promise::PromiseState status, + Node* result); + +- Node* AllocatePromiseReaction(Node* next, Node* payload, ++ Node* AllocatePromiseReaction(Node* next, Node* promise_or_capability, + Node* fulfill_handler, Node* reject_handler); + + Node* AllocatePromiseReactionJobTask(Heap::RootListIndex map_root_index, + Node* context, Node* argument, +- Node* handler, Node* payload); ++ Node* handler, ++ Node* promise_or_capability); + Node* AllocatePromiseReactionJobTask(Node* map, Node* context, Node* argument, +- Node* handler, Node* payload); ++ Node* handler, ++ Node* promise_or_capability); + Node* AllocatePromiseResolveThenableJobTask(Node* promise_to_resolve, + Node* then, Node* thenable, + Node* context); +@@ -192,7 +194,8 @@ class PromiseBuiltinsAssembler : public CodeStubAssembler { + Node* PromiseStatus(Node* promise); + + void PromiseReactionJob(Node* context, Node* argument, Node* handler, +- Node* payload, PromiseReaction::Type type); ++ Node* promise_or_capability, ++ PromiseReaction::Type type); + + Node* IsPromiseStatus(Node* actual, v8::Promise::PromiseState expected); + void PromiseSetStatus(Node* promise, v8::Promise::PromiseState status); +diff --git a/src/builtins/builtins.cc b/src/builtins/builtins.cc +index c348248fffb..7e6a0459a7d 100644 +--- a/src/builtins/builtins.cc ++++ b/src/builtins/builtins.cc +@@ -364,17 +364,12 @@ bool Builtins::IsIsolateIndependent(int index) { + case kAsyncFromSyncIteratorPrototypeNext: + case kAsyncFromSyncIteratorPrototypeReturn: + case kAsyncFromSyncIteratorPrototypeThrow: +- case kAsyncFunctionAwaitFulfill: +- case kAsyncFunctionAwaitReject: ++ case kAsyncFunctionAwaitCaught: + case kAsyncFunctionPromiseCreate: + case kAsyncFunctionPromiseRelease: +- case kAsyncGeneratorAwaitFulfill: +- case kAsyncGeneratorAwaitReject: + case kAsyncGeneratorResumeNext: +- case kAsyncGeneratorReturnClosedFulfill: +- case kAsyncGeneratorReturnClosedReject: +- case kAsyncGeneratorReturnFulfill: +- case kAsyncGeneratorYieldFulfill: ++ case kAsyncGeneratorReturnClosedRejectClosure: ++ case kAsyncGeneratorReturn: + case kAsyncIteratorValueUnwrap: + case kBitwiseNot: + case kBooleanPrototypeToString: +diff --git a/src/compiler/js-intrinsic-lowering.cc b/src/compiler/js-intrinsic-lowering.cc +index c570a1f8ddc..d9742e47d9f 100644 +--- a/src/compiler/js-intrinsic-lowering.cc ++++ b/src/compiler/js-intrinsic-lowering.cc +@@ -41,14 +41,6 @@ Reduction JSIntrinsicLowering::Reduce(Node* node) { + return ReduceCreateJSGeneratorObject(node); + case Runtime::kInlineGeneratorGetInputOrDebugPos: + return ReduceGeneratorGetInputOrDebugPos(node); +- case Runtime::kInlineAsyncFunctionAwaitCaught: +- return ReduceAsyncFunctionAwaitCaught(node); +- case Runtime::kInlineAsyncFunctionAwaitUncaught: +- return ReduceAsyncFunctionAwaitUncaught(node); +- case Runtime::kInlineAsyncGeneratorAwaitCaught: +- return ReduceAsyncGeneratorAwaitCaught(node); +- case Runtime::kInlineAsyncGeneratorAwaitUncaught: +- return ReduceAsyncGeneratorAwaitUncaught(node); + case Runtime::kInlineAsyncGeneratorReject: + return ReduceAsyncGeneratorReject(node); + case Runtime::kInlineAsyncGeneratorResolve: +@@ -185,33 +177,6 @@ Reduction JSIntrinsicLowering::ReduceGeneratorGetInputOrDebugPos(Node* node) { + return Change(node, op, generator, effect, control); + } + +-Reduction JSIntrinsicLowering::ReduceAsyncFunctionAwaitCaught(Node* node) { +- return Change( +- node, +- Builtins::CallableFor(isolate(), Builtins::kAsyncFunctionAwaitCaught), 0); +-} +- +-Reduction JSIntrinsicLowering::ReduceAsyncFunctionAwaitUncaught(Node* node) { +- return Change( +- node, +- Builtins::CallableFor(isolate(), Builtins::kAsyncFunctionAwaitUncaught), +- 0); +-} +- +-Reduction JSIntrinsicLowering::ReduceAsyncGeneratorAwaitCaught(Node* node) { +- return Change( +- node, +- Builtins::CallableFor(isolate(), Builtins::kAsyncGeneratorAwaitCaught), +- 0); +-} +- +-Reduction JSIntrinsicLowering::ReduceAsyncGeneratorAwaitUncaught(Node* node) { +- return Change( +- node, +- Builtins::CallableFor(isolate(), Builtins::kAsyncGeneratorAwaitUncaught), +- 0); +-} +- + Reduction JSIntrinsicLowering::ReduceAsyncGeneratorReject(Node* node) { + return Change( + node, Builtins::CallableFor(isolate(), Builtins::kAsyncGeneratorReject), +diff --git a/src/compiler/js-intrinsic-lowering.h b/src/compiler/js-intrinsic-lowering.h +index fb745986a60..18fe1248c7a 100644 +--- a/src/compiler/js-intrinsic-lowering.h ++++ b/src/compiler/js-intrinsic-lowering.h +@@ -45,10 +45,6 @@ class V8_EXPORT_PRIVATE JSIntrinsicLowering final + Reduction ReduceCreateJSGeneratorObject(Node* node); + Reduction ReduceGeneratorClose(Node* node); + Reduction ReduceGeneratorGetInputOrDebugPos(Node* node); +- Reduction ReduceAsyncFunctionAwaitCaught(Node* node); +- Reduction ReduceAsyncFunctionAwaitUncaught(Node* node); +- Reduction ReduceAsyncGeneratorAwaitCaught(Node* node); +- Reduction ReduceAsyncGeneratorAwaitUncaught(Node* node); + Reduction ReduceAsyncGeneratorReject(Node* node); + Reduction ReduceAsyncGeneratorResolve(Node* node); + Reduction ReduceAsyncGeneratorYield(Node* node); +diff --git a/src/contexts.h b/src/contexts.h +index 6fc6f2d1c32..fcfeccdc44e 100644 +--- a/src/contexts.h ++++ b/src/contexts.h +@@ -32,37 +32,44 @@ enum ContextLookupFlags { + // must always be allocated via Heap::AllocateContext() or + // Factory::NewContext. + +-#define NATIVE_CONTEXT_INTRINSIC_FUNCTIONS(V) \ +- V(ASYNC_FUNCTION_PROMISE_CREATE_INDEX, JSFunction, \ +- async_function_promise_create) \ +- V(ASYNC_FUNCTION_PROMISE_RELEASE_INDEX, JSFunction, \ +- async_function_promise_release) \ +- V(IS_ARRAYLIKE, JSFunction, is_arraylike) \ +- V(GENERATOR_NEXT_INTERNAL, JSFunction, generator_next_internal) \ +- V(MAKE_ERROR_INDEX, JSFunction, make_error) \ +- V(MAKE_RANGE_ERROR_INDEX, JSFunction, make_range_error) \ +- V(MAKE_SYNTAX_ERROR_INDEX, JSFunction, make_syntax_error) \ +- V(MAKE_TYPE_ERROR_INDEX, JSFunction, make_type_error) \ +- V(MAKE_URI_ERROR_INDEX, JSFunction, make_uri_error) \ +- V(OBJECT_CREATE, JSFunction, object_create) \ +- V(OBJECT_DEFINE_PROPERTIES, JSFunction, object_define_properties) \ +- V(OBJECT_DEFINE_PROPERTY, JSFunction, object_define_property) \ +- V(OBJECT_GET_PROTOTYPE_OF, JSFunction, object_get_prototype_of) \ +- V(OBJECT_IS_EXTENSIBLE, JSFunction, object_is_extensible) \ +- V(OBJECT_IS_FROZEN, JSFunction, object_is_frozen) \ +- V(OBJECT_IS_SEALED, JSFunction, object_is_sealed) \ +- V(OBJECT_KEYS, JSFunction, object_keys) \ +- V(REGEXP_INTERNAL_MATCH, JSFunction, regexp_internal_match) \ +- V(REFLECT_APPLY_INDEX, JSFunction, reflect_apply) \ +- V(REFLECT_CONSTRUCT_INDEX, JSFunction, reflect_construct) \ +- V(REFLECT_DEFINE_PROPERTY_INDEX, JSFunction, reflect_define_property) \ +- V(REFLECT_DELETE_PROPERTY_INDEX, JSFunction, reflect_delete_property) \ +- V(MATH_FLOOR_INDEX, JSFunction, math_floor) \ +- V(MATH_POW_INDEX, JSFunction, math_pow) \ +- V(PROMISE_INTERNAL_CONSTRUCTOR_INDEX, JSFunction, \ +- promise_internal_constructor) \ +- V(IS_PROMISE_INDEX, JSFunction, is_promise) \ +- V(PROMISE_THEN_INDEX, JSFunction, promise_then) ++#define NATIVE_CONTEXT_INTRINSIC_FUNCTIONS(V) \ ++ V(ASYNC_FUNCTION_AWAIT_CAUGHT_INDEX, JSFunction, \ ++ async_function_await_caught) \ ++ V(ASYNC_FUNCTION_AWAIT_UNCAUGHT_INDEX, JSFunction, \ ++ async_function_await_uncaught) \ ++ V(ASYNC_FUNCTION_PROMISE_CREATE_INDEX, JSFunction, \ ++ async_function_promise_create) \ ++ V(ASYNC_FUNCTION_PROMISE_RELEASE_INDEX, JSFunction, \ ++ async_function_promise_release) \ ++ V(IS_ARRAYLIKE, JSFunction, is_arraylike) \ ++ V(GENERATOR_NEXT_INTERNAL, JSFunction, generator_next_internal) \ ++ V(MAKE_ERROR_INDEX, JSFunction, make_error) \ ++ V(MAKE_RANGE_ERROR_INDEX, JSFunction, make_range_error) \ ++ V(MAKE_SYNTAX_ERROR_INDEX, JSFunction, make_syntax_error) \ ++ V(MAKE_TYPE_ERROR_INDEX, JSFunction, make_type_error) \ ++ V(MAKE_URI_ERROR_INDEX, JSFunction, make_uri_error) \ ++ V(OBJECT_CREATE, JSFunction, object_create) \ ++ V(OBJECT_DEFINE_PROPERTIES, JSFunction, object_define_properties) \ ++ V(OBJECT_DEFINE_PROPERTY, JSFunction, object_define_property) \ ++ V(OBJECT_GET_PROTOTYPE_OF, JSFunction, object_get_prototype_of) \ ++ V(OBJECT_IS_EXTENSIBLE, JSFunction, object_is_extensible) \ ++ V(OBJECT_IS_FROZEN, JSFunction, object_is_frozen) \ ++ V(OBJECT_IS_SEALED, JSFunction, object_is_sealed) \ ++ V(OBJECT_KEYS, JSFunction, object_keys) \ ++ V(REGEXP_INTERNAL_MATCH, JSFunction, regexp_internal_match) \ ++ V(REFLECT_APPLY_INDEX, JSFunction, reflect_apply) \ ++ V(REFLECT_CONSTRUCT_INDEX, JSFunction, reflect_construct) \ ++ V(REFLECT_DEFINE_PROPERTY_INDEX, JSFunction, reflect_define_property) \ ++ V(REFLECT_DELETE_PROPERTY_INDEX, JSFunction, reflect_delete_property) \ ++ V(MATH_FLOOR_INDEX, JSFunction, math_floor) \ ++ V(MATH_POW_INDEX, JSFunction, math_pow) \ ++ V(NEW_PROMISE_CAPABILITY_INDEX, JSFunction, new_promise_capability) \ ++ V(PROMISE_INTERNAL_CONSTRUCTOR_INDEX, JSFunction, \ ++ promise_internal_constructor) \ ++ V(IS_PROMISE_INDEX, JSFunction, is_promise) \ ++ V(PROMISE_THEN_INDEX, JSFunction, promise_then) \ ++ V(ASYNC_GENERATOR_AWAIT_CAUGHT, JSFunction, async_generator_await_caught) \ ++ V(ASYNC_GENERATOR_AWAIT_UNCAUGHT, JSFunction, async_generator_await_uncaught) + + #define NATIVE_CONTEXT_IMPORTED_FIELDS(V) \ + V(ARRAY_POP_INDEX, JSFunction, array_pop) \ +@@ -116,11 +123,27 @@ enum ContextLookupFlags { + V(ARRAY_BUFFER_NOINIT_FUN_INDEX, JSFunction, array_buffer_noinit_fun) \ + V(ARRAY_FUNCTION_INDEX, JSFunction, array_function) \ + V(ASYNC_FROM_SYNC_ITERATOR_MAP_INDEX, Map, async_from_sync_iterator_map) \ ++ V(ASYNC_FUNCTION_AWAIT_REJECT_SHARED_FUN, SharedFunctionInfo, \ ++ async_function_await_reject_shared_fun) \ ++ V(ASYNC_FUNCTION_AWAIT_RESOLVE_SHARED_FUN, SharedFunctionInfo, \ ++ async_function_await_resolve_shared_fun) \ + V(ASYNC_FUNCTION_FUNCTION_INDEX, JSFunction, async_function_constructor) \ + V(ASYNC_GENERATOR_FUNCTION_FUNCTION_INDEX, JSFunction, \ + async_generator_function_function) \ + V(ASYNC_ITERATOR_VALUE_UNWRAP_SHARED_FUN, SharedFunctionInfo, \ + async_iterator_value_unwrap_shared_fun) \ ++ V(ASYNC_GENERATOR_AWAIT_REJECT_SHARED_FUN, SharedFunctionInfo, \ ++ async_generator_await_reject_shared_fun) \ ++ V(ASYNC_GENERATOR_AWAIT_RESOLVE_SHARED_FUN, SharedFunctionInfo, \ ++ async_generator_await_resolve_shared_fun) \ ++ V(ASYNC_GENERATOR_YIELD_RESOLVE_SHARED_FUN, SharedFunctionInfo, \ ++ async_generator_yield_resolve_shared_fun) \ ++ V(ASYNC_GENERATOR_RETURN_RESOLVE_SHARED_FUN, SharedFunctionInfo, \ ++ async_generator_return_resolve_shared_fun) \ ++ V(ASYNC_GENERATOR_RETURN_CLOSED_RESOLVE_SHARED_FUN, SharedFunctionInfo, \ ++ async_generator_return_closed_resolve_shared_fun) \ ++ V(ASYNC_GENERATOR_RETURN_CLOSED_REJECT_SHARED_FUN, SharedFunctionInfo, \ ++ async_generator_return_closed_reject_shared_fun) \ + V(ATOMICS_OBJECT, JSObject, atomics_object) \ + V(BIGINT_FUNCTION_INDEX, JSFunction, bigint_function) \ + V(BIGINT64_ARRAY_FUN_INDEX, JSFunction, bigint64_array_fun) \ +diff --git a/src/heap-symbols.h b/src/heap-symbols.h +index 82ecd766575..c15aa9ba138 100644 +--- a/src/heap-symbols.h ++++ b/src/heap-symbols.h +@@ -237,7 +237,6 @@ + V(error_script_symbol) \ + V(error_start_pos_symbol) \ + V(frozen_symbol) \ +- V(generator_outer_promise_symbol) \ + V(generic_symbol) \ + V(home_object_symbol) \ + V(intl_initialized_marker_symbol) \ +diff --git a/src/interface-descriptors.h b/src/interface-descriptors.h +index 61da0c3f4ea..8375ea11971 100644 +--- a/src/interface-descriptors.h ++++ b/src/interface-descriptors.h +@@ -81,7 +81,6 @@ class PlatformInterfaceDescriptor; + V(FrameDropperTrampoline) \ + V(WasmRuntimeCall) \ + V(RunMicrotasks) \ +- V(PromiseReactionHandler) \ + BUILTIN_LIST_TFS(V) + + class V8_EXPORT_PRIVATE CallInterfaceDescriptorData { +@@ -889,13 +888,6 @@ class RunMicrotasksDescriptor final : public CallInterfaceDescriptor { + 0) + }; + +-class PromiseReactionHandlerDescriptor final : public CallInterfaceDescriptor { +- public: +- DEFINE_PARAMETERS(kArgument, kGenerator) +- DECLARE_DEFAULT_DESCRIPTOR(PromiseReactionHandlerDescriptor, +- CallInterfaceDescriptor, 2) +-}; +- + #define DEFINE_TFS_BUILTIN_DESCRIPTOR(Name, ...) \ + class Name##Descriptor : public CallInterfaceDescriptor { \ + public: \ +diff --git a/src/interpreter/bytecode-generator.cc b/src/interpreter/bytecode-generator.cc +index 29ad2c2a82f..744c6614f7a 100644 +--- a/src/interpreter/bytecode-generator.cc ++++ b/src/interpreter/bytecode-generator.cc +@@ -3239,20 +3239,22 @@ void BytecodeGenerator::BuildAwait(Expression* await_expr) { + // Await(operand) and suspend. + RegisterAllocationScope register_scope(this); + +- Runtime::FunctionId id; ++ int await_builtin_context_index; + RegisterList args; + if (IsAsyncGeneratorFunction(function_kind())) { +- id = catch_prediction() == HandlerTable::ASYNC_AWAIT +- ? Runtime::kInlineAsyncGeneratorAwaitUncaught +- : Runtime::kInlineAsyncGeneratorAwaitCaught; ++ await_builtin_context_index = ++ catch_prediction() == HandlerTable::ASYNC_AWAIT ++ ? Context::ASYNC_GENERATOR_AWAIT_UNCAUGHT ++ : Context::ASYNC_GENERATOR_AWAIT_CAUGHT; + args = register_allocator()->NewRegisterList(2); + builder() + ->MoveRegister(generator_object(), args[0]) + .StoreAccumulatorInRegister(args[1]); + } else { +- id = catch_prediction() == HandlerTable::ASYNC_AWAIT +- ? Runtime::kInlineAsyncFunctionAwaitUncaught +- : Runtime::kInlineAsyncFunctionAwaitCaught; ++ await_builtin_context_index = ++ catch_prediction() == HandlerTable::ASYNC_AWAIT ++ ? Context::ASYNC_FUNCTION_AWAIT_UNCAUGHT_INDEX ++ : Context::ASYNC_FUNCTION_AWAIT_CAUGHT_INDEX; + args = register_allocator()->NewRegisterList(3); + builder() + ->MoveRegister(generator_object(), args[0]) +@@ -3265,7 +3267,7 @@ void BytecodeGenerator::BuildAwait(Expression* await_expr) { + builder()->StoreAccumulatorInRegister(args[2]); + } + +- builder()->CallRuntime(id, args); ++ builder()->CallJSRuntime(await_builtin_context_index, args); + } + + BuildSuspendPoint(await_expr); +diff --git a/src/interpreter/interpreter-intrinsics-generator.cc b/src/interpreter/interpreter-intrinsics-generator.cc +index 675a8bcccc7..0480dec6cc6 100644 +--- a/src/interpreter/interpreter-intrinsics-generator.cc ++++ b/src/interpreter/interpreter-intrinsics-generator.cc +@@ -402,30 +402,6 @@ Node* IntrinsicsGenerator::GetImportMetaObject( + return return_value.value(); + } + +-Node* IntrinsicsGenerator::AsyncFunctionAwaitCaught( +- const InterpreterAssembler::RegListNodePair& args, Node* context) { +- return IntrinsicAsBuiltinCall(args, context, +- Builtins::kAsyncFunctionAwaitCaught); +-} +- +-Node* IntrinsicsGenerator::AsyncFunctionAwaitUncaught( +- const InterpreterAssembler::RegListNodePair& args, Node* context) { +- return IntrinsicAsBuiltinCall(args, context, +- Builtins::kAsyncFunctionAwaitUncaught); +-} +- +-Node* IntrinsicsGenerator::AsyncGeneratorAwaitCaught( +- const InterpreterAssembler::RegListNodePair& args, Node* context) { +- return IntrinsicAsBuiltinCall(args, context, +- Builtins::kAsyncGeneratorAwaitCaught); +-} +- +-Node* IntrinsicsGenerator::AsyncGeneratorAwaitUncaught( +- const InterpreterAssembler::RegListNodePair& args, Node* context) { +- return IntrinsicAsBuiltinCall(args, context, +- Builtins::kAsyncGeneratorAwaitUncaught); +-} +- + Node* IntrinsicsGenerator::AsyncGeneratorReject( + const InterpreterAssembler::RegListNodePair& args, Node* context) { + return IntrinsicAsBuiltinCall(args, context, Builtins::kAsyncGeneratorReject); +diff --git a/src/interpreter/interpreter-intrinsics.h b/src/interpreter/interpreter-intrinsics.h +index 6cdfec2d04f..3016183c0b9 100644 +--- a/src/interpreter/interpreter-intrinsics.h ++++ b/src/interpreter/interpreter-intrinsics.h +@@ -14,10 +14,6 @@ namespace interpreter { + // List of supported intrisics, with upper case name, lower case name and + // expected number of arguments (-1 denoting argument count is variable). + #define INTRINSICS_LIST(V) \ +- V(AsyncFunctionAwaitCaught, async_function_await_caught, 3) \ +- V(AsyncFunctionAwaitUncaught, async_function_await_uncaught, 3) \ +- V(AsyncGeneratorAwaitCaught, async_generator_await_caught, 2) \ +- V(AsyncGeneratorAwaitUncaught, async_generator_await_uncaught, 2) \ + V(AsyncGeneratorReject, async_generator_reject, 2) \ + V(AsyncGeneratorResolve, async_generator_resolve, 3) \ + V(AsyncGeneratorYield, async_generator_yield, 3) \ +diff --git a/src/isolate.cc b/src/isolate.cc +index adb30b12ace..2c4e22726d7 100644 +--- a/src/isolate.cc ++++ b/src/isolate.cc +@@ -2048,7 +2048,6 @@ void Isolate::PopPromise() { + } + + namespace { +- + bool InternalPromiseHasUserDefinedRejectHandler(Isolate* isolate, + Handle promise); + +@@ -2095,27 +2094,29 @@ bool InternalPromiseHasUserDefinedRejectHandler(Isolate* isolate, + } + + if (promise->status() == Promise::kPending) { +- Handle current(promise->reactions(), isolate); +- while (!current->IsSmi()) { +- Handle current_reaction = +- Handle::cast(current); +- Handle payload(current_reaction->payload(), isolate); +- Handle current_promise; +- if (JSPromise::From(payload).ToHandle(¤t_promise)) { +- if (current_reaction->reject_handler()->IsCallable()) { +- Handle current_handler( +- JSReceiver::cast(current_reaction->reject_handler()), isolate); +- if (PromiseHandlerCheck(isolate, current_handler, current_promise)) { +- return true; +- } +- } else { +- if (InternalPromiseHasUserDefinedRejectHandler(isolate, +- current_promise)) { +- return true; +- } ++ for (Handle current(promise->reactions(), isolate); ++ !current->IsSmi();) { ++ Handle reaction = Handle::cast(current); ++ Handle promise_or_capability( ++ reaction->promise_or_capability(), isolate); ++ Handle promise = Handle::cast( ++ promise_or_capability->IsJSPromise() ++ ? promise_or_capability ++ : handle(Handle::cast(promise_or_capability) ++ ->promise(), ++ isolate)); ++ if (reaction->reject_handler()->IsUndefined(isolate)) { ++ if (InternalPromiseHasUserDefinedRejectHandler(isolate, promise)) { ++ return true; ++ } ++ } else { ++ Handle current_handler( ++ JSReceiver::cast(reaction->reject_handler()), isolate); ++ if (PromiseHandlerCheck(isolate, current_handler, promise)) { ++ return true; + } + } +- current = handle(current_reaction->next(), isolate); ++ current = handle(reaction->next(), isolate); + } + } + +diff --git a/src/isolate.h b/src/isolate.h +index 75b447f1629..82d33033737 100644 +--- a/src/isolate.h ++++ b/src/isolate.h +@@ -1096,10 +1096,7 @@ class Isolate { + bool IsPromiseResolveLookupChainIntact(); + + // Make sure a lookup of "then" on any JSPromise whose [[Prototype]] is the +- // initial %PromisePrototype% yields the initial method. In addition this +- // protector also guards the negative lookup of "then" on the intrinsic +- // %ObjectPrototype%, meaning that such lookups are guaranteed to yield +- // undefined without triggering any side-effects. ++ // initial %PromisePrototype% yields the initial method. + bool IsPromiseThenLookupChainIntact(); + bool IsPromiseThenLookupChainIntact(Handle receiver); + +diff --git a/src/lookup.cc b/src/lookup.cc +index 20501149947..a4cca33d6c3 100644 +--- a/src/lookup.cc ++++ b/src/lookup.cc +@@ -364,14 +364,7 @@ void LookupIterator::InternalUpdateProtector() { + if (!isolate_->IsPromiseThenLookupChainIntact()) return; + // Setting the "then" property on any JSPromise instance or on the + // initial %PromisePrototype% invalidates the Promise#then protector. +- // Also setting the "then" property on the initial %ObjectPrototype% +- // invalidates the Promise#then protector, since we use this protector +- // to guard the fast-path in AsyncGeneratorResolve, where we can skip +- // the ResolvePromise step and go directly to FulfillPromise if we +- // know that the Object.prototype doesn't contain a "then" method. + if (holder_->IsJSPromise() || +- isolate_->IsInAnyContext(*holder_, +- Context::INITIAL_OBJECT_PROTOTYPE_INDEX) || + isolate_->IsInAnyContext(*holder_, Context::PROMISE_PROTOTYPE_INDEX)) { + isolate_->InvalidatePromiseThenProtector(); + } +diff --git a/src/objects-debug.cc b/src/objects-debug.cc +index c735cc0813c..086078bb251 100644 +--- a/src/objects-debug.cc ++++ b/src/objects-debug.cc +@@ -1172,13 +1172,10 @@ void PromiseReactionJobTask::PromiseReactionJobTaskVerify() { + VerifyHeapPointer(context()); + CHECK(context()->IsContext()); + VerifyHeapPointer(handler()); +- VerifyHeapPointer(payload()); +- if (handler()->IsCode()) { +- CHECK(payload()->IsJSReceiver()); +- } else { +- CHECK(handler()->IsUndefined(isolate) || handler()->IsCallable()); +- CHECK(payload()->IsJSPromise() || payload()->IsPromiseCapability()); +- } ++ CHECK(handler()->IsUndefined(isolate) || handler()->IsCallable()); ++ VerifyHeapPointer(promise_or_capability()); ++ CHECK(promise_or_capability()->IsJSPromise() || ++ promise_or_capability()->IsPromiseCapability()); + } + + void PromiseFulfillReactionJobTask::PromiseFulfillReactionJobTaskVerify() { +@@ -1220,18 +1217,14 @@ void PromiseReaction::PromiseReactionVerify() { + VerifyPointer(next()); + CHECK(next()->IsSmi() || next()->IsPromiseReaction()); + VerifyHeapPointer(reject_handler()); ++ CHECK(reject_handler()->IsUndefined(isolate) || ++ reject_handler()->IsCallable()); + VerifyHeapPointer(fulfill_handler()); +- VerifyHeapPointer(payload()); +- if (reject_handler()->IsCode()) { +- CHECK(fulfill_handler()->IsCode()); +- CHECK(payload()->IsJSReceiver()); +- } else { +- CHECK(reject_handler()->IsUndefined(isolate) || +- reject_handler()->IsCallable()); +- CHECK(fulfill_handler()->IsUndefined(isolate) || +- fulfill_handler()->IsCallable()); +- CHECK(payload()->IsJSPromise() || payload()->IsPromiseCapability()); +- } ++ CHECK(fulfill_handler()->IsUndefined(isolate) || ++ fulfill_handler()->IsCallable()); ++ VerifyHeapPointer(promise_or_capability()); ++ CHECK(promise_or_capability()->IsJSPromise() || ++ promise_or_capability()->IsPromiseCapability()); + } + + void JSPromise::JSPromiseVerify() { +diff --git a/src/objects-inl.h b/src/objects-inl.h +index bda031e0637..297e9fc836d 100644 +--- a/src/objects-inl.h ++++ b/src/objects-inl.h +@@ -2278,7 +2278,7 @@ ACCESSORS(JSGlobalProxy, native_context, Object, kNativeContextOffset) + ACCESSORS(AccessorInfo, name, Name, kNameOffset) + SMI_ACCESSORS(AccessorInfo, flags, kFlagsOffset) + ACCESSORS(AccessorInfo, expected_receiver_type, Object, +- kExpectedReceiverTypeOffset) ++ kExpectedReceiverTypeOffset) + + ACCESSORS_CHECKED2(AccessorInfo, getter, Object, kGetterOffset, true, + Foreign::IsNormalized(value)) +diff --git a/src/objects-printer.cc b/src/objects-printer.cc +index 942b9de0ba2..8d20279b2f1 100644 +--- a/src/objects-printer.cc ++++ b/src/objects-printer.cc +@@ -1441,7 +1441,7 @@ void PromiseFulfillReactionJobTask::PromiseFulfillReactionJobTaskPrint( + os << "\n - argument: " << Brief(argument()); + os << "\n - context: " << Brief(context()); + os << "\n - handler: " << Brief(handler()); +- os << "\n - payload: " << Brief(payload()); ++ os << "\n - promise_or_capability: " << Brief(promise_or_capability()); + os << "\n"; + } + +@@ -1451,7 +1451,7 @@ void PromiseRejectReactionJobTask::PromiseRejectReactionJobTaskPrint( + os << "\n - argument: " << Brief(argument()); + os << "\n - context: " << Brief(context()); + os << "\n - handler: " << Brief(handler()); +- os << "\n - payload: " << Brief(payload()); ++ os << "\n - promise_or_capability: " << Brief(promise_or_capability()); + os << "\n"; + } + +@@ -1478,7 +1478,7 @@ void PromiseReaction::PromiseReactionPrint(std::ostream& os) { // NOLINT + os << "\n - next: " << Brief(next()); + os << "\n - reject_handler: " << Brief(reject_handler()); + os << "\n - fulfill_handler: " << Brief(fulfill_handler()); +- os << "\n - payload: " << Brief(payload()); ++ os << "\n - promise_or_capability: " << Brief(promise_or_capability()); + os << "\n"; + } + +diff --git a/src/objects.cc b/src/objects.cc +index 8057cb837b1..6565910fd3f 100644 +--- a/src/objects.cc ++++ b/src/objects.cc +@@ -16054,27 +16054,6 @@ MaybeHandle JSPromise::Resolve(Handle promise, + return isolate->factory()->undefined_value(); + } + +-// static +-MaybeHandle JSPromise::From(Handle object) { +- Isolate* const isolate = object->GetIsolate(); +- if (object->IsJSPromise()) { +- return Handle::cast(object); +- } else if (object->IsPromiseCapability()) { +- Handle capability = +- Handle::cast(object); +- if (capability->promise()->IsJSPromise()) { +- return handle(JSPromise::cast(capability->promise()), isolate); +- } +- } else if (object->IsJSGeneratorObject()) { +- Handle generator = +- Handle::cast(object); +- Handle handled_by = JSObject::GetDataProperty( +- generator, isolate->factory()->generator_outer_promise_symbol()); +- if (handled_by->IsJSPromise()) return Handle::cast(handled_by); +- } +- return MaybeHandle(); +-} +- + // static + Handle JSPromise::TriggerPromiseReactions(Isolate* isolate, + Handle reactions, +@@ -16114,8 +16093,8 @@ Handle JSPromise::TriggerPromiseReactions(Isolate* isolate, + *isolate->native_context()); + STATIC_ASSERT(PromiseReaction::kFulfillHandlerOffset == + PromiseFulfillReactionJobTask::kHandlerOffset); +- STATIC_ASSERT(PromiseReaction::kPayloadOffset == +- PromiseFulfillReactionJobTask::kPayloadOffset); ++ STATIC_ASSERT(PromiseReaction::kPromiseOrCapabilityOffset == ++ PromiseFulfillReactionJobTask::kPromiseOrCapabilityOffset); + } else { + DisallowHeapAllocation no_gc; + HeapObject* handler = reaction->reject_handler(); +@@ -16125,8 +16104,8 @@ Handle JSPromise::TriggerPromiseReactions(Isolate* isolate, + Handle::cast(task)->set_context( + *isolate->native_context()); + Handle::cast(task)->set_handler(handler); +- STATIC_ASSERT(PromiseReaction::kPayloadOffset == +- PromiseRejectReactionJobTask::kPayloadOffset); ++ STATIC_ASSERT(PromiseReaction::kPromiseOrCapabilityOffset == ++ PromiseRejectReactionJobTask::kPromiseOrCapabilityOffset); + } + + isolate->EnqueueMicrotask(Handle::cast(task)); +diff --git a/src/objects/js-promise.h b/src/objects/js-promise.h +index 20a0a90131a..434bae89338 100644 +--- a/src/objects/js-promise.h ++++ b/src/objects/js-promise.h +@@ -59,12 +59,6 @@ class JSPromise : public JSObject { + V8_WARN_UNUSED_RESULT static MaybeHandle Resolve( + Handle promise, Handle resolution); + +- // This is a helper that extracts the JSPromise from the input +- // {object}, which is used as a payload for PromiseReaction and +- // PromiseReactionJobTask. +- V8_WARN_UNUSED_RESULT static MaybeHandle From( +- Handle object); +- + DECL_CAST(JSPromise) + + // Dispatched behavior. +diff --git a/src/objects/promise-inl.h b/src/objects/promise-inl.h +index 4283f0aa194..f9fb6110f34 100644 +--- a/src/objects/promise-inl.h ++++ b/src/objects/promise-inl.h +@@ -23,7 +23,8 @@ CAST_ACCESSOR(PromiseResolveThenableJobTask) + ACCESSORS(PromiseReaction, next, Object, kNextOffset) + ACCESSORS(PromiseReaction, reject_handler, HeapObject, kRejectHandlerOffset) + ACCESSORS(PromiseReaction, fulfill_handler, HeapObject, kFulfillHandlerOffset) +-ACCESSORS(PromiseReaction, payload, HeapObject, kPayloadOffset) ++ACCESSORS(PromiseReaction, promise_or_capability, HeapObject, ++ kPromiseOrCapabilityOffset) + + ACCESSORS(PromiseResolveThenableJobTask, context, Context, kContextOffset) + ACCESSORS(PromiseResolveThenableJobTask, promise_to_resolve, JSPromise, +@@ -34,7 +35,8 @@ ACCESSORS(PromiseResolveThenableJobTask, thenable, JSReceiver, kThenableOffset) + ACCESSORS(PromiseReactionJobTask, context, Context, kContextOffset) + ACCESSORS(PromiseReactionJobTask, argument, Object, kArgumentOffset); + ACCESSORS(PromiseReactionJobTask, handler, HeapObject, kHandlerOffset); +-ACCESSORS(PromiseReactionJobTask, payload, HeapObject, kPayloadOffset); ++ACCESSORS(PromiseReactionJobTask, promise_or_capability, HeapObject, ++ kPromiseOrCapabilityOffset); + + ACCESSORS(PromiseCapability, promise, HeapObject, kPromiseOffset) + ACCESSORS(PromiseCapability, resolve, Object, kResolveOffset) +diff --git a/src/objects/promise.h b/src/objects/promise.h +index 36ef4afe1d6..5ff5dac6f37 100644 +--- a/src/objects/promise.h ++++ b/src/objects/promise.h +@@ -26,16 +26,15 @@ class PromiseReactionJobTask : public Microtask { + public: + DECL_ACCESSORS(argument, Object) + DECL_ACCESSORS(context, Context) +- // [handler]: This is either a Code object, a Callable or Undefined. + DECL_ACCESSORS(handler, HeapObject) +- // [payload]: Usually a JSPromise or a PromiseCapability. +- DECL_ACCESSORS(payload, HeapObject) ++ // [promise_or_capability]: Either a JSPromise or a PromiseCapability. ++ DECL_ACCESSORS(promise_or_capability, HeapObject) + + static const int kArgumentOffset = Microtask::kHeaderSize; + static const int kContextOffset = kArgumentOffset + kPointerSize; + static const int kHandlerOffset = kContextOffset + kPointerSize; +- static const int kPayloadOffset = kHandlerOffset + kPointerSize; +- static const int kSize = kPayloadOffset + kPointerSize; ++ static const int kPromiseOrCapabilityOffset = kHandlerOffset + kPointerSize; ++ static const int kSize = kPromiseOrCapabilityOffset + kPointerSize; + + // Dispatched behavior. + DECL_CAST(PromiseReactionJobTask) +@@ -121,10 +120,9 @@ class PromiseCapability : public Struct { + // of microtasks. So the size of PromiseReaction and the size of the + // PromiseReactionJobTask has to be same for this to work. + // +-// The PromiseReaction::payload field usually holds a JSPromise +-// instance (in the fast case of a native promise) or a PromiseCapability +-// in case of a custom promise. For await we store the JSGeneratorObject +-// here and use custom Code handlers. ++// The PromiseReaction::promise_or_capability field can either hold a JSPromise ++// instance (in the fast case of a native promise) or a PromiseCapability in ++// case of a Promise subclass. + // + // We need to keep the context in the PromiseReaction so that we can run + // the default handlers (in case they are undefined) in the proper context. +@@ -138,18 +136,16 @@ class PromiseReaction : public Struct { + enum Type { kFulfill, kReject }; + + DECL_ACCESSORS(next, Object) +- // [reject_handler]: This is either a Code object, a Callable or Undefined. + DECL_ACCESSORS(reject_handler, HeapObject) +- // [fulfill_handler]: This is either a Code object, a Callable or Undefined. + DECL_ACCESSORS(fulfill_handler, HeapObject) +- // [payload]: Usually a JSPromise or a PromiseCapability. +- DECL_ACCESSORS(payload, HeapObject) ++ DECL_ACCESSORS(promise_or_capability, HeapObject) + + static const int kNextOffset = Struct::kHeaderSize; + static const int kRejectHandlerOffset = kNextOffset + kPointerSize; + static const int kFulfillHandlerOffset = kRejectHandlerOffset + kPointerSize; +- static const int kPayloadOffset = kFulfillHandlerOffset + kPointerSize; +- static const int kSize = kPayloadOffset + kPointerSize; ++ static const int kPromiseOrCapabilityOffset = ++ kFulfillHandlerOffset + kPointerSize; ++ static const int kSize = kPromiseOrCapabilityOffset + kPointerSize; + + // Dispatched behavior. + DECL_CAST(PromiseReaction) +diff --git a/src/runtime/runtime-generator.cc b/src/runtime/runtime-generator.cc +index e69d3340426..3c7c808c30b 100644 +--- a/src/runtime/runtime-generator.cc ++++ b/src/runtime/runtime-generator.cc +@@ -70,30 +70,6 @@ RUNTIME_FUNCTION(Runtime_GeneratorGetInputOrDebugPos) { + UNREACHABLE(); + } + +-RUNTIME_FUNCTION(Runtime_AsyncFunctionAwaitCaught) { +- // Runtime call is implemented in InterpreterIntrinsics and lowered in +- // JSIntrinsicLowering +- UNREACHABLE(); +-} +- +-RUNTIME_FUNCTION(Runtime_AsyncFunctionAwaitUncaught) { +- // Runtime call is implemented in InterpreterIntrinsics and lowered in +- // JSIntrinsicLowering +- UNREACHABLE(); +-} +- +-RUNTIME_FUNCTION(Runtime_AsyncGeneratorAwaitCaught) { +- // Runtime call is implemented in InterpreterIntrinsics and lowered in +- // JSIntrinsicLowering +- UNREACHABLE(); +-} +- +-RUNTIME_FUNCTION(Runtime_AsyncGeneratorAwaitUncaught) { +- // Runtime call is implemented in InterpreterIntrinsics and lowered in +- // JSIntrinsicLowering +- UNREACHABLE(); +-} +- + RUNTIME_FUNCTION(Runtime_AsyncGeneratorResolve) { + // Runtime call is implemented in InterpreterIntrinsics and lowered in + // JSIntrinsicLowering +diff --git a/src/runtime/runtime-promise.cc b/src/runtime/runtime-promise.cc +index b2a7e8bae1b..f5b9db3c028 100644 +--- a/src/runtime/runtime-promise.cc ++++ b/src/runtime/runtime-promise.cc +@@ -114,14 +114,13 @@ RUNTIME_FUNCTION(Runtime_PromiseHookInit) { + RUNTIME_FUNCTION(Runtime_PromiseHookBefore) { + HandleScope scope(isolate); + DCHECK_EQ(1, args.length()); +- CONVERT_ARG_HANDLE_CHECKED(HeapObject, payload, 0); +- Handle promise; +- if (JSPromise::From(payload).ToHandle(&promise)) { +- if (isolate->debug()->is_active()) isolate->PushPromise(promise); +- if (promise->IsJSPromise()) { +- isolate->RunPromiseHook(PromiseHookType::kBefore, promise, +- isolate->factory()->undefined_value()); +- } ++ CONVERT_ARG_HANDLE_CHECKED(JSReceiver, maybe_promise, 0); ++ if (!maybe_promise->IsJSPromise()) return isolate->heap()->undefined_value(); ++ Handle promise = Handle::cast(maybe_promise); ++ if (isolate->debug()->is_active()) isolate->PushPromise(promise); ++ if (promise->IsJSPromise()) { ++ isolate->RunPromiseHook(PromiseHookType::kBefore, promise, ++ isolate->factory()->undefined_value()); + } + return isolate->heap()->undefined_value(); + } +@@ -129,14 +128,13 @@ RUNTIME_FUNCTION(Runtime_PromiseHookBefore) { + RUNTIME_FUNCTION(Runtime_PromiseHookAfter) { + HandleScope scope(isolate); + DCHECK_EQ(1, args.length()); +- CONVERT_ARG_HANDLE_CHECKED(HeapObject, payload, 0); +- Handle promise; +- if (JSPromise::From(payload).ToHandle(&promise)) { +- if (isolate->debug()->is_active()) isolate->PopPromise(); +- if (promise->IsJSPromise()) { +- isolate->RunPromiseHook(PromiseHookType::kAfter, promise, +- isolate->factory()->undefined_value()); +- } ++ CONVERT_ARG_HANDLE_CHECKED(JSReceiver, maybe_promise, 0); ++ if (!maybe_promise->IsJSPromise()) return isolate->heap()->undefined_value(); ++ Handle promise = Handle::cast(maybe_promise); ++ if (isolate->debug()->is_active()) isolate->PopPromise(); ++ if (promise->IsJSPromise()) { ++ isolate->RunPromiseHook(PromiseHookType::kAfter, promise, ++ isolate->factory()->undefined_value()); + } + return isolate->heap()->undefined_value(); + } +diff --git a/src/runtime/runtime.h b/src/runtime/runtime.h +index 48a63d500da..37ce74e8250 100644 +--- a/src/runtime/runtime.h ++++ b/src/runtime/runtime.h +@@ -222,10 +222,6 @@ namespace internal { + F(SetNativeFlag, 1, 1) + + #define FOR_EACH_INTRINSIC_GENERATOR(F) \ +- F(AsyncFunctionAwaitCaught, 3, 1) \ +- F(AsyncFunctionAwaitUncaught, 3, 1) \ +- F(AsyncGeneratorAwaitCaught, 2, 1) \ +- F(AsyncGeneratorAwaitUncaught, 2, 1) \ + F(AsyncGeneratorHasCatchHandlerForPC, 1, 1) \ + F(AsyncGeneratorReject, 2, 1) \ + F(AsyncGeneratorResolve, 3, 1) \ +diff --git a/test/cctest/interpreter/bytecode_expectations/AsyncGenerators.golden b/test/cctest/interpreter/bytecode_expectations/AsyncGenerators.golden +index df6b3723586..2b4eb6b2cc5 100644 +--- a/test/cctest/interpreter/bytecode_expectations/AsyncGenerators.golden ++++ b/test/cctest/interpreter/bytecode_expectations/AsyncGenerators.golden +@@ -39,7 +39,7 @@ bytecodes: [ + B(LdaUndefined), + B(Star), R(6), + B(Mov), R(0), R(5), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncGeneratorAwaitUncaught), R(5), U8(2), ++ B(CallJSRuntime), U8(%async_generator_await_uncaught), R(5), U8(2), + B(SuspendGenerator), R(0), R(0), U8(5), U8(1), + B(ResumeGenerator), R(0), R(0), U8(5), + B(Star), R(5), +@@ -166,7 +166,7 @@ bytecodes: [ + B(LdaUndefined), + B(Star), R(6), + B(Mov), R(0), R(5), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncGeneratorAwaitUncaught), R(5), U8(2), ++ B(CallJSRuntime), U8(%async_generator_await_uncaught), R(5), U8(2), + B(SuspendGenerator), R(0), R(0), U8(5), U8(2), + B(ResumeGenerator), R(0), R(0), U8(5), + B(Star), R(5), +@@ -404,7 +404,7 @@ bytecodes: [ + B(LdaUndefined), + B(Star), R(16), + B(Mov), R(2), R(15), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncGeneratorAwaitUncaught), R(15), U8(2), ++ B(CallJSRuntime), U8(%async_generator_await_uncaught), R(15), U8(2), + B(SuspendGenerator), R(2), R(0), U8(15), U8(2), + B(ResumeGenerator), R(2), R(0), U8(15), + B(Star), R(15), +@@ -580,7 +580,7 @@ bytecodes: [ + B(Jump), U8(2), + B(Star), R(13), + B(Mov), R(0), R(12), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncGeneratorAwaitUncaught), R(12), U8(2), ++ B(CallJSRuntime), U8(%async_generator_await_uncaught), R(12), U8(2), + /* 49 E> */ B(SuspendGenerator), R(0), R(0), U8(12), U8(1), + B(ResumeGenerator), R(0), R(0), U8(12), + B(Star), R(12), +@@ -598,7 +598,7 @@ bytecodes: [ + B(CallRuntime), U16(Runtime::kThrowThrowMethodMissing), R(0), U8(0), + B(Star), R(13), + B(Mov), R(0), R(12), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncGeneratorAwaitUncaught), R(12), U8(2), ++ B(CallJSRuntime), U8(%async_generator_await_uncaught), R(12), U8(2), + /* 49 E> */ B(SuspendGenerator), R(0), R(0), U8(12), U8(2), + B(ResumeGenerator), R(0), R(0), U8(12), + B(Star), R(12), +@@ -639,7 +639,7 @@ bytecodes: [ + B(LdaUndefined), + B(Star), R(6), + B(Mov), R(0), R(5), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncGeneratorAwaitUncaught), R(5), U8(2), ++ B(CallJSRuntime), U8(%async_generator_await_uncaught), R(5), U8(2), + B(SuspendGenerator), R(0), R(0), U8(5), U8(4), + B(ResumeGenerator), R(0), R(0), U8(5), + B(Star), R(5), +diff --git a/test/cctest/interpreter/bytecode_expectations/ForAwaitOf.golden b/test/cctest/interpreter/bytecode_expectations/ForAwaitOf.golden +index 95400dacf80..4d36315f027 100644 +--- a/test/cctest/interpreter/bytecode_expectations/ForAwaitOf.golden ++++ b/test/cctest/interpreter/bytecode_expectations/ForAwaitOf.golden +@@ -53,7 +53,7 @@ bytecodes: [ + B(Star), R(21), + B(Mov), R(2), R(20), + B(Mov), R(11), R(22), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(20), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(20), U8(3), + /* 40 E> */ B(SuspendGenerator), R(2), R(0), U8(20), U8(0), + B(ResumeGenerator), R(2), R(0), U8(20), + B(Star), R(20), +@@ -137,7 +137,7 @@ bytecodes: [ + B(Star), R(21), + B(Mov), R(2), R(20), + B(Mov), R(11), R(22), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitCaught), R(20), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_caught), R(20), U8(3), + B(SuspendGenerator), R(2), R(0), U8(20), U8(1), + B(ResumeGenerator), R(2), R(0), U8(20), + B(Star), R(20), +@@ -160,7 +160,7 @@ bytecodes: [ + B(Star), R(20), + B(Mov), R(2), R(19), + B(Mov), R(11), R(21), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(19), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(19), U8(3), + B(SuspendGenerator), R(2), R(0), U8(19), U8(2), + B(ResumeGenerator), R(2), R(0), U8(19), + B(Star), R(19), +@@ -306,7 +306,7 @@ bytecodes: [ + B(Star), R(21), + B(Mov), R(2), R(20), + B(Mov), R(11), R(22), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(20), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(20), U8(3), + /* 40 E> */ B(SuspendGenerator), R(2), R(0), U8(20), U8(0), + B(ResumeGenerator), R(2), R(0), U8(20), + B(Star), R(20), +@@ -391,7 +391,7 @@ bytecodes: [ + B(Star), R(21), + B(Mov), R(2), R(20), + B(Mov), R(11), R(22), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitCaught), R(20), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_caught), R(20), U8(3), + B(SuspendGenerator), R(2), R(0), U8(20), U8(1), + B(ResumeGenerator), R(2), R(0), U8(20), + B(Star), R(20), +@@ -414,7 +414,7 @@ bytecodes: [ + B(Star), R(20), + B(Mov), R(2), R(19), + B(Mov), R(11), R(21), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(19), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(19), U8(3), + B(SuspendGenerator), R(2), R(0), U8(19), U8(2), + B(ResumeGenerator), R(2), R(0), U8(19), + B(Star), R(19), +@@ -575,7 +575,7 @@ bytecodes: [ + B(Star), R(21), + B(Mov), R(2), R(20), + B(Mov), R(11), R(22), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(20), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(20), U8(3), + /* 40 E> */ B(SuspendGenerator), R(2), R(0), U8(20), U8(0), + B(ResumeGenerator), R(2), R(0), U8(20), + B(Star), R(20), +@@ -667,7 +667,7 @@ bytecodes: [ + B(Star), R(21), + B(Mov), R(2), R(20), + B(Mov), R(11), R(22), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitCaught), R(20), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_caught), R(20), U8(3), + B(SuspendGenerator), R(2), R(0), U8(20), U8(1), + B(ResumeGenerator), R(2), R(0), U8(20), + B(Star), R(20), +@@ -690,7 +690,7 @@ bytecodes: [ + B(Star), R(20), + B(Mov), R(2), R(19), + B(Mov), R(11), R(21), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(19), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(19), U8(3), + B(SuspendGenerator), R(2), R(0), U8(19), U8(2), + B(ResumeGenerator), R(2), R(0), U8(19), + B(Star), R(19), +diff --git a/test/cctest/interpreter/bytecode_expectations/ForOfLoop.golden b/test/cctest/interpreter/bytecode_expectations/ForOfLoop.golden +index 1a0155da79c..f92076e6e65 100644 +--- a/test/cctest/interpreter/bytecode_expectations/ForOfLoop.golden ++++ b/test/cctest/interpreter/bytecode_expectations/ForOfLoop.golden +@@ -1196,7 +1196,7 @@ bytecodes: [ + /* 45 S> */ B(Mov), R(2), R(21), + B(Mov), R(0), R(22), + B(Mov), R(11), R(23), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(21), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(21), U8(3), + /* 45 E> */ B(SuspendGenerator), R(2), R(0), U8(21), U8(0), + B(ResumeGenerator), R(2), R(0), U8(21), + B(Star), R(21), +diff --git a/test/cctest/interpreter/bytecode_expectations/StandardForLoop.golden b/test/cctest/interpreter/bytecode_expectations/StandardForLoop.golden +index 80609db7b80..7edf446ce33 100644 +--- a/test/cctest/interpreter/bytecode_expectations/StandardForLoop.golden ++++ b/test/cctest/interpreter/bytecode_expectations/StandardForLoop.golden +@@ -493,7 +493,7 @@ bytecodes: [ + /* 52 S> */ B(Mov), R(1), R(7), + B(Mov), R(0), R(8), + B(Mov), R(2), R(9), +- B(InvokeIntrinsic), U8(Runtime::k_AsyncFunctionAwaitUncaught), R(7), U8(3), ++ B(CallJSRuntime), U8(%async_function_await_uncaught), R(7), U8(3), + /* 52 E> */ B(SuspendGenerator), R(1), R(0), U8(7), U8(0), + B(ResumeGenerator), R(1), R(0), U8(7), + B(Star), R(7), +diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc +index 2f552a9d9d9..8b93944d933 100644 +--- a/test/cctest/test-api.cc ++++ b/test/cctest/test-api.cc +@@ -18358,12 +18358,6 @@ TEST(PromiseHook) { + CHECK_EQ(v8::Promise::kFulfilled, GetPromise("p")->State()); + CHECK_EQ(9, promise_hook_data->promise_hook_count); + +- promise_hook_data->Reset(); +- source = "(async() => await p)();\n"; +- +- CompileRun(source); +- CHECK_EQ(11, promise_hook_data->promise_hook_count); +- + delete promise_hook_data; + isolate->SetPromiseHook(nullptr); + } +diff --git a/tools/v8heapconst.py b/tools/v8heapconst.py +index 1e57ce64a9e..e3b29f82042 100644 +--- a/tools/v8heapconst.py ++++ b/tools/v8heapconst.py +@@ -263,12 +263,12 @@ + ("MAP_SPACE", 0x04511): (173, "Tuple2Map"), + ("MAP_SPACE", 0x04569): (171, "ScriptMap"), + ("MAP_SPACE", 0x045c1): (163, "InterceptorInfoMap"), +- ("MAP_SPACE", 0x04619): (154, "AccessorInfoMap"), +- ("MAP_SPACE", 0x04671): (153, "AccessCheckInfoMap"), +- ("MAP_SPACE", 0x046c9): (155, "AccessorPairMap"), +- ("MAP_SPACE", 0x04721): (156, "AliasedArgumentsEntryMap"), +- ("MAP_SPACE", 0x04779): (157, "AllocationMementoMap"), +- ("MAP_SPACE", 0x047d1): (158, "AllocationSiteMap"), ++ ("MAP_SPACE", 0x04619): (158, "AllocationSiteMap"), ++ ("MAP_SPACE", 0x04671): (154, "AccessorInfoMap"), ++ ("MAP_SPACE", 0x046c9): (153, "AccessCheckInfoMap"), ++ ("MAP_SPACE", 0x04721): (155, "AccessorPairMap"), ++ ("MAP_SPACE", 0x04779): (156, "AliasedArgumentsEntryMap"), ++ ("MAP_SPACE", 0x047d1): (157, "AllocationMementoMap"), + ("MAP_SPACE", 0x04829): (159, "AsyncGeneratorRequestMap"), + ("MAP_SPACE", 0x04881): (160, "ContextExtensionMap"), + ("MAP_SPACE", 0x048d9): (161, "DebugInfoMap"), +@@ -366,4 +366,4 @@ + "NATIVE", + ) + +-# This set of constants is generated from a shipping build. ++# This set of constants is generated from a non-shipping build. diff --git a/patches/common/v8/backport_9fb02b526.patch b/patches/common/v8/backport_9fb02b526.patch new file mode 100644 index 00000000000..5ffb19e7d23 --- /dev/null +++ b/patches/common/v8/backport_9fb02b526.patch @@ -0,0 +1,114 @@ +9fb02b526f1cd3b859a530a01adb08bc0d089f4f +diff --git a/src/builtins/builtins-api.cc b/src/builtins/builtins-api.cc +index 7e2d3e219e..c26c1a9fd1 100644 +--- a/src/builtins/builtins-api.cc ++++ b/src/builtins/builtins-api.cc +@@ -22,17 +22,21 @@ namespace { + // Returns the holder JSObject if the function can legally be called with this + // receiver. Returns nullptr if the call is illegal. + // TODO(dcarney): CallOptimization duplicates this logic, merge. +-JSObject* GetCompatibleReceiver(Isolate* isolate, FunctionTemplateInfo* info, +- JSObject* receiver) { ++JSReceiver* GetCompatibleReceiver(Isolate* isolate, FunctionTemplateInfo* info, ++ JSReceiver* receiver) { + Object* recv_type = info->signature(); + // No signature, return holder. + if (!recv_type->IsFunctionTemplateInfo()) return receiver; ++ // A Proxy cannot have been created from the signature template. ++ if (!receiver->IsJSObject()) return nullptr; ++ ++ JSObject* js_obj_receiver = JSObject::cast(receiver); + FunctionTemplateInfo* signature = FunctionTemplateInfo::cast(recv_type); + + // Check the receiver. Fast path for receivers with no hidden prototypes. +- if (signature->IsTemplateFor(receiver)) return receiver; +- if (!receiver->map()->has_hidden_prototype()) return nullptr; +- for (PrototypeIterator iter(isolate, receiver, kStartAtPrototype, ++ if (signature->IsTemplateFor(js_obj_receiver)) return receiver; ++ if (!js_obj_receiver->map()->has_hidden_prototype()) return nullptr; ++ for (PrototypeIterator iter(isolate, js_obj_receiver, kStartAtPrototype, + PrototypeIterator::END_AT_NON_HIDDEN); + !iter.IsAtEnd(); iter.Advance()) { + JSObject* current = iter.GetCurrent(); +@@ -46,8 +50,8 @@ V8_WARN_UNUSED_RESULT MaybeHandle HandleApiCallHelper( + Isolate* isolate, Handle function, + Handle new_target, Handle fun_data, + Handle receiver, BuiltinArguments args) { +- Handle js_receiver; +- JSObject* raw_holder; ++ Handle js_receiver; ++ JSReceiver* raw_holder; + if (is_construct) { + DCHECK(args.receiver()->IsTheHole(isolate)); + if (fun_data->instance_template()->IsUndefined(isolate)) { +@@ -69,21 +73,18 @@ V8_WARN_UNUSED_RESULT MaybeHandle HandleApiCallHelper( + raw_holder = *js_receiver; + } else { + DCHECK(receiver->IsJSReceiver()); +- +- if (!receiver->IsJSObject()) { +- // This function cannot be called with the given receiver. Abort! +- THROW_NEW_ERROR( +- isolate, NewTypeError(MessageTemplate::kIllegalInvocation), Object); +- } +- +- js_receiver = Handle::cast(receiver); ++ js_receiver = Handle::cast(receiver); + + if (!fun_data->accept_any_receiver() && +- js_receiver->IsAccessCheckNeeded() && +- !isolate->MayAccess(handle(isolate->context()), js_receiver)) { +- isolate->ReportFailedAccessCheck(js_receiver); +- RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object); +- return isolate->factory()->undefined_value(); ++ js_receiver->IsAccessCheckNeeded()) { ++ // Proxies never need access checks. ++ DCHECK(js_receiver->IsJSObject()); ++ Handle js_obj_receiver = Handle::cast(js_receiver); ++ if (!isolate->MayAccess(handle(isolate->context()), js_obj_receiver)) { ++ isolate->ReportFailedAccessCheck(js_obj_receiver); ++ RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object); ++ return isolate->factory()->undefined_value(); ++ } + } + + raw_holder = GetCompatibleReceiver(isolate, *fun_data, *js_receiver); +diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc +index 7887cbfa75..0605f439e5 100644 +--- a/test/cctest/test-api.cc ++++ b/test/cctest/test-api.cc +@@ -1088,6 +1088,34 @@ THREADED_PROFILED_TEST(FunctionTemplate) { + TestFunctionTemplateAccessor(construct_callback, Return239Callback); + } + ++static void FunctionCallbackForProxyTest( ++ const v8::FunctionCallbackInfo& info) { ++ info.GetReturnValue().Set(info.This()); ++} ++ ++THREADED_TEST(FunctionTemplateWithProxy) { ++ LocalContext env; ++ v8::Isolate* isolate = env->GetIsolate(); ++ v8::HandleScope scope(isolate); ++ ++ v8::Local function_template = ++ v8::FunctionTemplate::New(isolate, FunctionCallbackForProxyTest); ++ v8::Local function = ++ function_template->GetFunction(env.local()).ToLocalChecked(); ++ CHECK((*env)->Global()->Set(env.local(), v8_str("f"), function).FromJust()); ++ v8::Local proxy = ++ CompileRun("var proxy = new Proxy({}, {}); proxy"); ++ CHECK(proxy->IsProxy()); ++ ++ v8::Local result = CompileRun("f(proxy)"); ++ CHECK(result->Equals(env.local(), (*env)->Global()).FromJust()); ++ ++ result = CompileRun("f.call(proxy)"); ++ CHECK(result->Equals(env.local(), proxy).FromJust()); ++ ++ result = CompileRun("Reflect.apply(f, proxy, [1])"); ++ CHECK(result->Equals(env.local(), proxy).FromJust()); ++} + + static void SimpleCallback(const v8::FunctionCallbackInfo& info) { + ApiTestFuzzer::Fuzz(); diff --git a/patches/common/v8/backport_aa6ce3e.patch b/patches/common/v8/backport_aa6ce3e.patch new file mode 100644 index 00000000000..77b3afc58c5 --- /dev/null +++ b/patches/common/v8/backport_aa6ce3e.patch @@ -0,0 +1,1243 @@ +diff --git a/include/v8-profiler.h b/include/v8-profiler.h +index cbd988e9e9..37ff09a0dd 100644 +--- a/include/v8-profiler.h ++++ b/include/v8-profiler.h +@@ -1009,6 +1009,76 @@ struct HeapStatsUpdate { + uint32_t size; // New value of size field for the interval with this index. + }; + ++#define CODE_EVENTS_LIST(V) \ ++ V(Builtin) \ ++ V(Callback) \ ++ V(Eval) \ ++ V(Function) \ ++ V(InterpretedFunction) \ ++ V(Handler) \ ++ V(BytecodeHandler) \ ++ V(LazyCompile) \ ++ V(RegExp) \ ++ V(Script) \ ++ V(Stub) ++ ++/** ++ * Note that this enum may be extended in the future. Please include a default ++ * case if this enum is used in a switch statement. ++ */ ++enum CodeEventType { ++ kUnknownType = 0 ++#define V(Name) , k##Name##Type ++ CODE_EVENTS_LIST(V) ++#undef V ++}; ++ ++/** ++ * Representation of a code creation event ++ */ ++class V8_EXPORT CodeEvent { ++ public: ++ uintptr_t GetCodeStartAddress(); ++ size_t GetCodeSize(); ++ Local GetFunctionName(); ++ Local GetScriptName(); ++ int GetScriptLine(); ++ int GetScriptColumn(); ++ /** ++ * NOTE (mmarchini): We can't allocate objects in the heap when we collect ++ * existing code, and both the code type and the comment are not stored in the ++ * heap, so we return those as const char*. ++ */ ++ CodeEventType GetCodeType(); ++ const char* GetComment(); ++ ++ static const char* GetCodeEventTypeName(CodeEventType code_event_type); ++}; ++ ++/** ++ * Interface to listen to code creation events. ++ */ ++class V8_EXPORT CodeEventHandler { ++ public: ++ /** ++ * Creates a new listener for the |isolate|. The isolate must be initialized. ++ * The listener object must be disposed after use by calling |Dispose| method. ++ * Multiple listeners can be created for the same isolate. ++ */ ++ explicit CodeEventHandler(Isolate* isolate); ++ virtual ~CodeEventHandler(); ++ ++ virtual void Handle(CodeEvent* code_event) = 0; ++ ++ void Enable(); ++ void Disable(); ++ ++ private: ++ CodeEventHandler(); ++ CodeEventHandler(const CodeEventHandler&); ++ CodeEventHandler& operator=(const CodeEventHandler&); ++ void* internal_listener_; ++}; + + } // namespace v8 + +diff --git a/src/api.cc b/src/api.cc +index 2943703e74..c6bcc8165b 100644 +--- a/src/api.cc ++++ b/src/api.cc +@@ -10162,6 +10162,70 @@ void CpuProfiler::SetIdle(bool is_idle) { + isolate->SetIdle(is_idle); + } + ++uintptr_t CodeEvent::GetCodeStartAddress() { ++ return reinterpret_cast(this)->code_start_address; ++} ++ ++size_t CodeEvent::GetCodeSize() { ++ return reinterpret_cast(this)->code_size; ++} ++ ++Local CodeEvent::GetFunctionName() { ++ return ToApiHandle( ++ reinterpret_cast(this)->function_name); ++} ++ ++Local CodeEvent::GetScriptName() { ++ return ToApiHandle( ++ reinterpret_cast(this)->script_name); ++} ++ ++int CodeEvent::GetScriptLine() { ++ return reinterpret_cast(this)->script_line; ++} ++ ++int CodeEvent::GetScriptColumn() { ++ return reinterpret_cast(this)->script_column; ++} ++ ++CodeEventType CodeEvent::GetCodeType() { ++ return reinterpret_cast(this)->code_type; ++} ++ ++const char* CodeEvent::GetComment() { ++ return reinterpret_cast(this)->comment; ++} ++ ++const char* CodeEvent::GetCodeEventTypeName(CodeEventType code_event_type) { ++ switch (code_event_type) { ++ case kUnknownType: ++ return "Unknown"; ++#define V(Name) \ ++ case k##Name##Type: \ ++ return #Name; ++ CODE_EVENTS_LIST(V) ++#undef V ++ } ++} ++ ++CodeEventHandler::CodeEventHandler(Isolate* isolate) { ++ internal_listener_ = ++ new i::ExternalCodeEventListener(reinterpret_cast(isolate)); ++} ++ ++CodeEventHandler::~CodeEventHandler() { ++ delete reinterpret_cast(internal_listener_); ++} ++ ++void CodeEventHandler::Enable() { ++ reinterpret_cast(internal_listener_) ++ ->StartListening(this); ++} ++ ++void CodeEventHandler::Disable() { ++ reinterpret_cast(internal_listener_) ++ ->StopListening(); ++} + + static i::HeapGraphEdge* ToInternal(const HeapGraphEdge* edge) { + return const_cast( +diff --git a/src/code-events.h b/src/code-events.h +index 439cb54dca..caed5160f4 100644 +--- a/src/code-events.h ++++ b/src/code-events.h +@@ -24,32 +24,38 @@ class WasmCode; + using WasmName = Vector; + } // namespace wasm + +-#define LOG_EVENTS_AND_TAGS_LIST(V) \ +- V(CODE_CREATION_EVENT, "code-creation") \ +- V(CODE_DISABLE_OPT_EVENT, "code-disable-optimization") \ +- V(CODE_MOVE_EVENT, "code-move") \ +- V(CODE_DELETE_EVENT, "code-delete") \ +- V(CODE_MOVING_GC, "code-moving-gc") \ +- V(SHARED_FUNC_MOVE_EVENT, "sfi-move") \ +- V(SNAPSHOT_CODE_NAME_EVENT, "snapshot-code-name") \ +- V(TICK_EVENT, "tick") \ +- V(BUILTIN_TAG, "Builtin") \ +- V(CALLBACK_TAG, "Callback") \ +- V(EVAL_TAG, "Eval") \ +- V(FUNCTION_TAG, "Function") \ +- V(INTERPRETED_FUNCTION_TAG, "InterpretedFunction") \ +- V(HANDLER_TAG, "Handler") \ +- V(BYTECODE_HANDLER_TAG, "BytecodeHandler") \ +- V(LAZY_COMPILE_TAG, "LazyCompile") \ +- V(REG_EXP_TAG, "RegExp") \ +- V(SCRIPT_TAG, "Script") \ +- V(STUB_TAG, "Stub") \ +- V(NATIVE_FUNCTION_TAG, "Function") \ +- V(NATIVE_LAZY_COMPILE_TAG, "LazyCompile") \ +- V(NATIVE_SCRIPT_TAG, "Script") ++#define LOG_EVENTS_LIST(V) \ ++ V(CODE_CREATION_EVENT, code-creation) \ ++ V(CODE_DISABLE_OPT_EVENT, code-disable-optimization) \ ++ V(CODE_MOVE_EVENT, code-move) \ ++ V(CODE_DELETE_EVENT, code-delete) \ ++ V(CODE_MOVING_GC, code-moving-gc) \ ++ V(SHARED_FUNC_MOVE_EVENT, sfi-move) \ ++ V(SNAPSHOT_CODE_NAME_EVENT, snapshot-code-name) \ ++ V(TICK_EVENT, tick) ++ ++#define TAGS_LIST(V) \ ++ V(BUILTIN_TAG, Builtin) \ ++ V(CALLBACK_TAG, Callback) \ ++ V(EVAL_TAG, Eval) \ ++ V(FUNCTION_TAG, Function) \ ++ V(INTERPRETED_FUNCTION_TAG, InterpretedFunction) \ ++ V(HANDLER_TAG, Handler) \ ++ V(BYTECODE_HANDLER_TAG, BytecodeHandler) \ ++ V(LAZY_COMPILE_TAG, LazyCompile) \ ++ V(REG_EXP_TAG, RegExp) \ ++ V(SCRIPT_TAG, Script) \ ++ V(STUB_TAG, Stub) \ ++ V(NATIVE_FUNCTION_TAG, Function) \ ++ V(NATIVE_LAZY_COMPILE_TAG, LazyCompile) \ ++ V(NATIVE_SCRIPT_TAG, Script) + // Note that 'NATIVE_' cases for functions and scripts are mapped onto + // original tags when writing to the log. + ++#define LOG_EVENTS_AND_TAGS_LIST(V) \ ++ LOG_EVENTS_LIST(V) \ ++ TAGS_LIST(V) ++ + #define PROFILE(the_isolate, Call) (the_isolate)->code_event_dispatcher()->Call; + + class CodeEventListener { +@@ -85,6 +91,8 @@ class CodeEventListener { + enum DeoptKind { kSoft, kLazy, kEager }; + virtual void CodeDeoptEvent(Code* code, DeoptKind kind, Address pc, + int fp_to_sp_delta) = 0; ++ ++ virtual bool is_listening_to_code_events() { return false; } + }; + + class CodeEventDispatcher { +@@ -101,6 +109,14 @@ class CodeEventDispatcher { + base::LockGuard guard(&mutex_); + listeners_.erase(listener); + } ++ bool IsListeningToCodeEvents() { ++ for (auto it : listeners_) { ++ if (it->is_listening_to_code_events()) { ++ return true; ++ } ++ } ++ return false; ++ } + + #define CODE_EVENT_DISPATCH(code) \ + base::LockGuard guard(&mutex_); \ +diff --git a/src/compiler.cc b/src/compiler.cc +index ae6bc9c4fa..a01750b23a 100644 +--- a/src/compiler.cc ++++ b/src/compiler.cc +@@ -84,8 +84,9 @@ void LogFunctionCompilation(CodeEventListener::LogEventsAndTags tag, + // Log the code generation. If source information is available include + // script name and line number. Check explicitly whether logging is + // enabled as finding the line number is not free. +- if (!isolate->logger()->is_logging_code_events() && +- !isolate->is_profiling() && !FLAG_log_function_events) { ++ if (!isolate->logger()->is_listening_to_code_events() && ++ !isolate->is_profiling() && !FLAG_log_function_events && ++ !isolate->code_event_dispatcher()->IsListeningToCodeEvents()) { + return; + } + +diff --git a/src/compiler/wasm-compiler.cc b/src/compiler/wasm-compiler.cc +index 7cc26321b6..ad2600eecc 100644 +--- a/src/compiler/wasm-compiler.cc ++++ b/src/compiler/wasm-compiler.cc +@@ -3948,7 +3948,8 @@ Node* WasmGraphBuilder::AtomicOp(wasm::WasmOpcode opcode, Node* const* inputs, + + namespace { + bool must_record_function_compilation(Isolate* isolate) { +- return isolate->logger()->is_logging_code_events() || isolate->is_profiling(); ++ return isolate->logger()->is_listening_to_code_events() || ++ isolate->is_profiling(); + } + + PRINTF_FORMAT(4, 5) +diff --git a/src/heap/mark-compact.cc b/src/heap/mark-compact.cc +index 53aa615e47..c84fa2f69c 100644 +--- a/src/heap/mark-compact.cc ++++ b/src/heap/mark-compact.cc +@@ -2414,7 +2414,7 @@ void MarkCompactCollectorBase::CreateAndExecuteEvacuationTasks( + + const bool profiling = + heap()->isolate()->is_profiling() || +- heap()->isolate()->logger()->is_logging_code_events() || ++ heap()->isolate()->logger()->is_listening_to_code_events() || + heap()->isolate()->heap_profiler()->is_tracking_object_moves() || + heap()->has_heap_object_allocation_tracker(); + ProfilingMigrationObserver profiling_observer(heap()); +diff --git a/src/isolate.cc b/src/isolate.cc +index c4036784a6..9ac61a6bea 100644 +--- a/src/isolate.cc ++++ b/src/isolate.cc +@@ -2893,7 +2893,7 @@ void CreateOffHeapTrampolines(Isolate* isolate) { + // thus collected by the GC. + builtins->set_builtin(i, *trampoline); + +- if (isolate->logger()->is_logging_code_events() || ++ if (isolate->logger()->is_listening_to_code_events() || + isolate->is_profiling()) { + isolate->logger()->LogCodeObject(*trampoline); + } +diff --git a/src/isolate.h b/src/isolate.h +index 50aab84487..4f7b550bfa 100644 +--- a/src/isolate.h ++++ b/src/isolate.h +@@ -57,6 +57,7 @@ class BuiltinsConstantsTableBuilder; + class CallInterfaceDescriptorData; + class CancelableTaskManager; + class CodeEventDispatcher; ++class ExternalCodeEventListener; + class CodeGenerator; + class CodeRange; + class CodeStubDescriptor; +diff --git a/src/log.cc b/src/log.cc +index 953216aef7..563fe3c5f0 100644 +--- a/src/log.cc ++++ b/src/log.cc +@@ -40,11 +40,33 @@ + namespace v8 { + namespace internal { + +-#define DECLARE_EVENT(ignore1, name) name, ++#define DECLARE_EVENT(ignore1, name) #name, + static const char* kLogEventsNames[CodeEventListener::NUMBER_OF_LOG_EVENTS] = { + LOG_EVENTS_AND_TAGS_LIST(DECLARE_EVENT)}; + #undef DECLARE_EVENT + ++static v8::CodeEventType GetCodeEventTypeForTag( ++ CodeEventListener::LogEventsAndTags tag) { ++ switch (tag) { ++ case CodeEventListener::NUMBER_OF_LOG_EVENTS: ++#define V(Event, _) case CodeEventListener::Event: ++ LOG_EVENTS_LIST(V) ++#undef V ++ return v8::CodeEventType::kUnknownType; ++#define V(From, To) \ ++ case CodeEventListener::From: \ ++ return v8::CodeEventType::k##To##Type; ++ TAGS_LIST(V) ++#undef V ++ } ++} ++#define CALL_CODE_EVENT_HANDLER(Call) \ ++ if (listener_) { \ ++ listener_->Call; \ ++ } else { \ ++ PROFILE(isolate_, Call); \ ++ } ++ + static const char* ComputeMarker(SharedFunctionInfo* shared, + AbstractCode* code) { + switch (code->kind()) { +@@ -319,9 +341,147 @@ void PerfBasicLogger::LogRecordedBuffer(const wasm::WasmCode* code, + code->instructions().length(), name, length); + } + +-// Low-level logging support. +-#define LL_LOG(Call) if (ll_logger_) ll_logger_->Call; ++// External CodeEventListener ++ExternalCodeEventListener::ExternalCodeEventListener(Isolate* isolate) ++ : is_listening_(false), isolate_(isolate), code_event_handler_(nullptr) {} ++ ++ExternalCodeEventListener::~ExternalCodeEventListener() { ++ if (is_listening_) { ++ StopListening(); ++ } ++} ++ ++void ExternalCodeEventListener::LogExistingCode() { ++ HandleScope scope(isolate_); ++ ExistingCodeLogger logger(isolate_, this); ++ logger.LogCodeObjects(); ++ logger.LogBytecodeHandlers(); ++ logger.LogCompiledFunctions(); ++} ++ ++void ExternalCodeEventListener::StartListening( ++ CodeEventHandler* code_event_handler) { ++ if (is_listening_ || code_event_handler == nullptr) { ++ return; ++ } ++ code_event_handler_ = code_event_handler; ++ is_listening_ = isolate_->code_event_dispatcher()->AddListener(this); ++ if (is_listening_) { ++ LogExistingCode(); ++ } ++} + ++void ExternalCodeEventListener::StopListening() { ++ if (!is_listening_) { ++ return; ++ } ++ ++ isolate_->code_event_dispatcher()->RemoveListener(this); ++ is_listening_ = false; ++} ++ ++void ExternalCodeEventListener::CodeCreateEvent( ++ CodeEventListener::LogEventsAndTags tag, AbstractCode* code, ++ const char* comment) { ++ CodeEvent code_event; ++ code_event.code_start_address = ++ reinterpret_cast(code->InstructionStart()); ++ code_event.code_size = static_cast(code->InstructionSize()); ++ code_event.function_name = isolate_->factory()->empty_string(); ++ code_event.script_name = isolate_->factory()->empty_string(); ++ code_event.script_line = 0; ++ code_event.script_column = 0; ++ code_event.code_type = GetCodeEventTypeForTag(tag); ++ code_event.comment = comment; ++ ++ code_event_handler_->Handle(reinterpret_cast(&code_event)); ++} ++ ++void ExternalCodeEventListener::CodeCreateEvent( ++ CodeEventListener::LogEventsAndTags tag, AbstractCode* code, Name* name) { ++ Handle name_string = ++ Name::ToFunctionName(Handle(name, isolate_)).ToHandleChecked(); ++ ++ CodeEvent code_event; ++ code_event.code_start_address = ++ reinterpret_cast(code->InstructionStart()); ++ code_event.code_size = static_cast(code->InstructionSize()); ++ code_event.function_name = name_string; ++ code_event.script_name = isolate_->factory()->empty_string(); ++ code_event.script_line = 0; ++ code_event.script_column = 0; ++ code_event.code_type = GetCodeEventTypeForTag(tag); ++ code_event.comment = ""; ++ ++ code_event_handler_->Handle(reinterpret_cast(&code_event)); ++} ++ ++void ExternalCodeEventListener::CodeCreateEvent( ++ CodeEventListener::LogEventsAndTags tag, AbstractCode* code, ++ SharedFunctionInfo* shared, Name* name) { ++ Handle name_string = ++ Name::ToFunctionName(Handle(name, isolate_)).ToHandleChecked(); ++ ++ CodeEvent code_event; ++ code_event.code_start_address = ++ reinterpret_cast(code->InstructionStart()); ++ code_event.code_size = static_cast(code->InstructionSize()); ++ code_event.function_name = name_string; ++ code_event.script_name = isolate_->factory()->empty_string(); ++ code_event.script_line = 0; ++ code_event.script_column = 0; ++ code_event.code_type = GetCodeEventTypeForTag(tag); ++ code_event.comment = ""; ++ ++ code_event_handler_->Handle(reinterpret_cast(&code_event)); ++} ++ ++void ExternalCodeEventListener::CodeCreateEvent( ++ CodeEventListener::LogEventsAndTags tag, AbstractCode* code, ++ SharedFunctionInfo* shared, Name* source, int line, int column) { ++ Handle name_string = ++ Name::ToFunctionName(Handle(shared->Name(), isolate_)) ++ .ToHandleChecked(); ++ Handle source_string = ++ Name::ToFunctionName(Handle(source, isolate_)).ToHandleChecked(); ++ ++ CodeEvent code_event; ++ code_event.code_start_address = ++ reinterpret_cast(code->InstructionStart()); ++ code_event.code_size = static_cast(code->InstructionSize()); ++ code_event.function_name = name_string; ++ code_event.script_name = source_string; ++ code_event.script_line = line; ++ code_event.script_column = column; ++ code_event.code_type = GetCodeEventTypeForTag(tag); ++ code_event.comment = ""; ++ ++ code_event_handler_->Handle(reinterpret_cast(&code_event)); ++} ++ ++void ExternalCodeEventListener::CodeCreateEvent(LogEventsAndTags tag, ++ const wasm::WasmCode* code, ++ wasm::WasmName name) { ++ // TODO(mmarchini): handle later ++} ++ ++void ExternalCodeEventListener::RegExpCodeCreateEvent(AbstractCode* code, ++ String* source) { ++ CodeEvent code_event; ++ code_event.code_start_address = ++ reinterpret_cast(code->InstructionStart()); ++ code_event.code_size = static_cast(code->InstructionSize()); ++ code_event.function_name = Handle(source, isolate_); ++ code_event.script_name = isolate_->factory()->empty_string(); ++ code_event.script_line = 0; ++ code_event.script_column = 0; ++ code_event.code_type = GetCodeEventTypeForTag(CodeEventListener::REG_EXP_TAG); ++ code_event.comment = ""; ++ ++ code_event_handler_->Handle(reinterpret_cast(&code_event)); ++} ++ ++// Low-level logging support. + class LowLevelLogger : public CodeEventLogger { + public: + explicit LowLevelLogger(const char* file_name); +@@ -808,7 +968,8 @@ Logger::Logger(Isolate* isolate) + perf_jit_logger_(nullptr), + ll_logger_(nullptr), + jit_logger_(nullptr), +- is_initialized_(false) {} ++ is_initialized_(false), ++ existing_code_logger_(isolate) {} + + Logger::~Logger() { + delete log_; +@@ -1077,7 +1238,7 @@ void AppendCodeCreateHeader(Log::MessageBuilder& msg, + + void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + AbstractCode* code, const char* comment) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + Log::MessageBuilder msg(log_); + AppendCodeCreateHeader(msg, tag, code, &timer_); +@@ -1087,7 +1248,7 @@ void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + + void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + AbstractCode* code, Name* name) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + Log::MessageBuilder msg(log_); + AppendCodeCreateHeader(msg, tag, code, &timer_); +@@ -1098,7 +1259,7 @@ void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + AbstractCode* code, SharedFunctionInfo* shared, + Name* name) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + if (code == AbstractCode::cast( + isolate_->builtins()->builtin(Builtins::kCompileLazy))) { +@@ -1114,7 +1275,7 @@ void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + + void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + const wasm::WasmCode* code, wasm::WasmName name) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + Log::MessageBuilder msg(log_); + AppendCodeCreateHeader(msg, tag, AbstractCode::Kind::WASM_FUNCTION, +@@ -1142,7 +1303,7 @@ void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + AbstractCode* code, SharedFunctionInfo* shared, + Name* source, int line, int column) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + + Log::MessageBuilder msg(log_); +@@ -1259,7 +1420,7 @@ void Logger::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag, + + void Logger::CodeDisableOptEvent(AbstractCode* code, + SharedFunctionInfo* shared) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + Log::MessageBuilder msg(log_); + msg << kLogEventsNames[CodeEventListener::CODE_DISABLE_OPT_EVENT] << kNext +@@ -1270,13 +1431,13 @@ void Logger::CodeDisableOptEvent(AbstractCode* code, + + + void Logger::CodeMovingGCEvent() { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!log_->IsEnabled() || !FLAG_ll_prof) return; + base::OS::SignalCodeMovingGC(); + } + + void Logger::RegExpCodeCreateEvent(AbstractCode* code, String* source) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + if (!FLAG_log_code || !log_->IsEnabled()) return; + Log::MessageBuilder msg(log_); + AppendCodeCreateHeader(msg, CodeEventListener::REG_EXP_TAG, code, &timer_); +@@ -1285,7 +1446,7 @@ void Logger::RegExpCodeCreateEvent(AbstractCode* code, String* source) { + } + + void Logger::CodeMoveEvent(AbstractCode* from, Address to) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + MoveEventInternal(CodeEventListener::CODE_MOVE_EVENT, from->address(), to); + } + +@@ -1334,7 +1495,7 @@ void Logger::CodeNameEvent(Address addr, int pos, const char* code_name) { + + + void Logger::SharedFunctionInfoMoveEvent(Address from, Address to) { +- if (!is_logging_code_events()) return; ++ if (!is_listening_to_code_events()) return; + MoveEventInternal(CodeEventListener::SHARED_FUNC_MOVE_EVENT, from, to); + } + +@@ -1624,170 +1785,28 @@ static int EnumerateWasmModules(Heap* heap, + } + + void Logger::LogCodeObject(Object* object) { +- AbstractCode* code_object = AbstractCode::cast(object); +- CodeEventListener::LogEventsAndTags tag = CodeEventListener::STUB_TAG; +- const char* description = "Unknown code from the snapshot"; +- switch (code_object->kind()) { +- case AbstractCode::INTERPRETED_FUNCTION: +- case AbstractCode::OPTIMIZED_FUNCTION: +- return; // We log this later using LogCompiledFunctions. +- case AbstractCode::BYTECODE_HANDLER: +- return; // We log it later by walking the dispatch table. +- case AbstractCode::STUB: +- description = +- CodeStub::MajorName(CodeStub::GetMajorKey(code_object->GetCode())); +- if (description == nullptr) description = "A stub from the snapshot"; +- tag = CodeEventListener::STUB_TAG; +- break; +- case AbstractCode::REGEXP: +- description = "Regular expression code"; +- tag = CodeEventListener::REG_EXP_TAG; +- break; +- case AbstractCode::BUILTIN: +- description = +- isolate_->builtins()->name(code_object->GetCode()->builtin_index()); +- tag = CodeEventListener::BUILTIN_TAG; +- break; +- case AbstractCode::WASM_FUNCTION: +- description = "A Wasm function"; +- tag = CodeEventListener::FUNCTION_TAG; +- break; +- case AbstractCode::JS_TO_WASM_FUNCTION: +- description = "A JavaScript to Wasm adapter"; +- tag = CodeEventListener::STUB_TAG; +- break; +- case AbstractCode::WASM_TO_JS_FUNCTION: +- description = "A Wasm to JavaScript adapter"; +- tag = CodeEventListener::STUB_TAG; +- break; +- case AbstractCode::WASM_INTERPRETER_ENTRY: +- description = "A Wasm to Interpreter adapter"; +- tag = CodeEventListener::STUB_TAG; +- break; +- case AbstractCode::C_WASM_ENTRY: +- description = "A C to Wasm entry stub"; +- tag = CodeEventListener::STUB_TAG; +- break; +- case AbstractCode::NUMBER_OF_KINDS: +- UNIMPLEMENTED(); +- } +- PROFILE(isolate_, CodeCreateEvent(tag, code_object, description)); ++ existing_code_logger_.LogCodeObject(object); + } + +-void Logger::LogCodeObjects() { +- Heap* heap = isolate_->heap(); +- HeapIterator iterator(heap); +- DisallowHeapAllocation no_gc; +- for (HeapObject* obj = iterator.next(); obj != nullptr; +- obj = iterator.next()) { +- if (obj->IsCode()) LogCodeObject(obj); +- if (obj->IsBytecodeArray()) LogCodeObject(obj); +- } +-} ++void Logger::LogCodeObjects() { existing_code_logger_.LogCodeObjects(); } + + void Logger::LogBytecodeHandler(interpreter::Bytecode bytecode, + interpreter::OperandScale operand_scale, + Code* code) { +- std::string bytecode_name = +- interpreter::Bytecodes::ToString(bytecode, operand_scale); +- PROFILE(isolate_, +- CodeCreateEvent(CodeEventListener::BYTECODE_HANDLER_TAG, +- AbstractCode::cast(code), bytecode_name.c_str())); ++ existing_code_logger_.LogBytecodeHandler(bytecode, operand_scale, code); + } + + void Logger::LogBytecodeHandlers() { +- const interpreter::OperandScale kOperandScales[] = { +-#define VALUE(Name, _) interpreter::OperandScale::k##Name, +- OPERAND_SCALE_LIST(VALUE) +-#undef VALUE +- }; +- +- const int last_index = static_cast(interpreter::Bytecode::kLast); +- interpreter::Interpreter* interpreter = isolate_->interpreter(); +- for (auto operand_scale : kOperandScales) { +- for (int index = 0; index <= last_index; ++index) { +- interpreter::Bytecode bytecode = interpreter::Bytecodes::FromByte(index); +- if (interpreter::Bytecodes::BytecodeHasHandler(bytecode, operand_scale)) { +- Code* code = interpreter->GetBytecodeHandler(bytecode, operand_scale); +- if (isolate_->heap()->IsDeserializeLazyHandler(code)) continue; +- LogBytecodeHandler(bytecode, operand_scale, code); +- } +- } +- } ++ existing_code_logger_.LogBytecodeHandlers(); + } + + void Logger::LogExistingFunction(Handle shared, + Handle code) { +- if (shared->script()->IsScript()) { +- Handle