From 1fa998d8919375312d20d6d54bae955d166031c7 Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 10:35:58 -0600 Subject: [EME] Make WidevineAdapter compatible with CDM version 9 NOTE: this breaks compatibility with CDM version 8. --- dom/media/gmp/widevine-adapter/WidevineAdapter.cpp | 4 +- .../gmp/widevine-adapter/WidevineDecryptor.cpp | 63 +++++++++++----------- dom/media/gmp/widevine-adapter/WidevineDecryptor.h | 24 ++++----- dom/media/gmp/widevine-adapter/WidevineUtils.cpp | 2 +- dom/media/gmp/widevine-adapter/WidevineUtils.h | 6 +-- .../gmp/widevine-adapter/WidevineVideoDecoder.h | 2 +- 6 files changed, 51 insertions(+), 50 deletions(-) diff --git a/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp b/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp index 74b5c38e8..fa703ab0b 100644 --- a/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp @@ -46,7 +46,7 @@ void* GetCdmHost(int aHostInterfaceVersion, void* aUserData) Log("GetCdmHostFunc(%d, %p)", aHostInterfaceVersion, aUserData); WidevineDecryptor* decryptor = reinterpret_cast(aUserData); MOZ_ASSERT(decryptor); - return static_cast(decryptor); + return static_cast(decryptor); } #define STRINGIFY(s) _STRINGIFY(s) @@ -162,7 +162,7 @@ WidevineAdapter::Supports(int32_t aModuleVersion, { return aModuleVersion == CDM_MODULE_VERSION && aInterfaceVersion == cdm::ContentDecryptionModule::kVersion && - aHostVersion == cdm::Host_8::kVersion; + aHostVersion == cdm::Host_9::kVersion; } } // namespace mozilla diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp index 149fa1701..e85aa2db3 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp @@ -301,6 +301,12 @@ WidevineDecryptor::GetCurrentWallTime() return base::Time::Now().ToDoubleT(); } +void +ChromiumCDMChild::OnResolveKeyStatusPromise(uint32_t aPromiseId, + cdm::KeyStatus aKeyStatus) { + //TODO: The callback of GetStatusForPolicy. See Mozilla bug 1404230. +} + void WidevineDecryptor::OnResolveNewSessionPromise(uint32_t aPromiseId, const char* aSessionId, @@ -332,42 +338,41 @@ WidevineDecryptor::OnResolvePromise(uint32_t aPromiseId) mCallback->ResolvePromise(aPromiseId); } -static GMPDOMException -ToGMPDOMException(cdm::Error aError) -{ - switch (aError) { - case kNotSupportedError: return kGMPNotSupportedError; - case kInvalidStateError: return kGMPInvalidStateError; - case kInvalidAccessError: - // Note: Chrome converts kInvalidAccessError to TypeError, since the - // Chromium CDM API doesn't have a type error enum value. The EME spec - // requires TypeError in some places, so we do the same conversion. - // See bug 1313202. - return kGMPTypeError; - case kQuotaExceededError: return kGMPQuotaExceededError; - case kUnknownError: return kGMPInvalidModificationError; // Note: Unique placeholder. - case kClientError: return kGMPAbortError; // Note: Unique placeholder. - case kOutputError: return kGMPSecurityError; // Note: Unique placeholder. - }; - return kGMPTimeoutError; // Note: Unique placeholder. +// Align with spec, the Exceptions used by CDM to reject promises . +// https://w3c.github.io/encrypted-media/#exceptions +cdm::Exception +ConvertCDMErrorToCDMException(cdm::Error error) { + switch (error) { + case cdm::kNotSupportedError: + return cdm::Exception::kExceptionNotSupportedError; + case cdm::kInvalidStateError: + return cdm::Exception::kExceptionInvalidStateError; + case cdm::kInvalidAccessError: + return cdm::Exception::kExceptionTypeError; + case cdm::kQuotaExceededError: + return cdm::Exception::kExceptionQuotaExceededError; + break; + } + + return cdm::Exception::kExceptionInvalidStateError; } void WidevineDecryptor::OnRejectPromise(uint32_t aPromiseId, - Error aError, - uint32_t aSystemCode, - const char* aErrorMessage, - uint32_t aErrorMessageSize) + cdm::Exception aException, + uint32_t aSystemCode, + const char* aErrorMessage, + uint32_t aErrorMessageSize) { if (!mCallback) { Log("Decryptor::OnRejectPromise(aPromiseId=%d, err=%d, sysCode=%u, msg=%s) FAIL; !mCallback", - aPromiseId, (int)aError, aSystemCode, aErrorMessage); + aPromiseId, (int)aException, aSystemCode, aErrorMessage); return; } Log("Decryptor::OnRejectPromise(aPromiseId=%d, err=%d, sysCode=%u, msg=%s)", aPromiseId, (int)aError, aSystemCode, aErrorMessage); mCallback->RejectPromise(aPromiseId, - ToGMPDOMException(aError), + ToGMPDOMException(aException), !aErrorMessageSize ? "" : aErrorMessage, aErrorMessageSize); } @@ -385,12 +390,10 @@ ToGMPMessageType(MessageType message_type) void WidevineDecryptor::OnSessionMessage(const char* aSessionId, - uint32_t aSessionIdSize, - MessageType aMessageType, - const char* aMessage, - uint32_t aMessageSize, - const char* aLegacyDestinationUrl, - uint32_t aLegacyDestinationUrlLength) + uint32_t aSessionIdSize, + cdm::MessageType aMessageType, + const char* aMessage, + uint32_t aMessageSize) { if (!mCallback) { Log("Decryptor::OnSessionMessage() FAIL; !mCallback"); diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.h b/dom/media/gmp/widevine-adapter/WidevineDecryptor.h index d5185192b..c1a1ebaa1 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.h +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.h @@ -16,7 +16,7 @@ namespace mozilla { class WidevineDecryptor : public GMPDecryptor - , public cdm::Host_8 + , public cdm::Host_9 { public: @@ -69,16 +69,19 @@ public: void DecryptingComplete() override; - // cdm::Host_8 + // cdm::Host_9 implementation cdm::Buffer* Allocate(uint32_t aCapacity) override; void SetTimer(int64_t aDelayMs, void* aContext) override; cdm::Time GetCurrentWallTime() override; + // cdm::Host_9 interface + void OnResolveKeyStatusPromise(uint32_t aPromiseId, + cdm::KeyStatus aKeyStatus) override; void OnResolveNewSessionPromise(uint32_t aPromiseId, const char* aSessionId, uint32_t aSessionIdSize) override; void OnResolvePromise(uint32_t aPromiseId) override; void OnRejectPromise(uint32_t aPromiseId, - cdm::Error aError, + cdm::Exception aException, uint32_t aSystemCode, const char* aErrorMessage, uint32_t aErrorMessageSize) override; @@ -86,9 +89,7 @@ public: uint32_t aSessionIdSize, cdm::MessageType aMessageType, const char* aMessage, - uint32_t aMessageSize, - const char* aLegacyDestinationUrl, - uint32_t aLegacyDestinationUrlLength) override; + uint32_t aMessageSize) override; void OnSessionKeysChange(const char* aSessionId, uint32_t aSessionIdSize, bool aHasAdditionalUsableKey, @@ -99,12 +100,6 @@ public: cdm::Time aNewExpiryTime) override; void OnSessionClosed(const char* aSessionId, uint32_t aSessionIdSize) override; - void OnLegacySessionError(const char* aSessionId, - uint32_t aSessionId_length, - cdm::Error aError, - uint32_t aSystemCode, - const char* aErrorMessage, - uint32_t aErrorMessageLength) override; void SendPlatformChallenge(const char* aServiceId, uint32_t aServiceIdSize, const char* aChallenge, @@ -113,6 +108,9 @@ public: void QueryOutputProtectionStatus() override; void OnDeferredInitializationDone(cdm::StreamType aStreamType, cdm::Status aDecoderStatus) override; + // cdm::Host_9 interface + // NOTE: the interface has changed upstream. + void RequestStorageId() override {} cdm::FileIO* CreateFileIO(cdm::FileIOClient* aClient) override; GMPDecryptorCallback* Callback() const { return mCallback; } @@ -120,7 +118,7 @@ public: private: ~WidevineDecryptor(); RefPtr mCDM; - cdm::ContentDecryptionModule_8* CDM() { return mCDM->GetCDM(); } + cdm::ContentDecryptionModule_9* CDM() { return mCDM->GetCDM(); } GMPDecryptorCallback* mCallback; std::map mPromiseIdToNewSessionTokens; diff --git a/dom/media/gmp/widevine-adapter/WidevineUtils.cpp b/dom/media/gmp/widevine-adapter/WidevineUtils.cpp index 925dfe1a1..deb71e51a 100644 --- a/dom/media/gmp/widevine-adapter/WidevineUtils.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineUtils.cpp @@ -77,7 +77,7 @@ void InitInputBuffer(const GMPEncryptedBufferMetadata* aCrypto, aInputBuffer.timestamp = aTimestamp; } -CDMWrapper::CDMWrapper(cdm::ContentDecryptionModule_8* aCDM, +CDMWrapper::CDMWrapper(cdm::ContentDecryptionModule_9* aCDM, WidevineDecryptor* aDecryptor) : mCDM(aCDM) , mDecryptor(aDecryptor) diff --git a/dom/media/gmp/widevine-adapter/WidevineUtils.h b/dom/media/gmp/widevine-adapter/WidevineUtils.h index 57c004a87..ca65ff881 100644 --- a/dom/media/gmp/widevine-adapter/WidevineUtils.h +++ b/dom/media/gmp/widevine-adapter/WidevineUtils.h @@ -48,12 +48,12 @@ class CDMWrapper { public: NS_INLINE_DECL_THREADSAFE_REFCOUNTING(CDMWrapper) - explicit CDMWrapper(cdm::ContentDecryptionModule_8* aCDM, + explicit CDMWrapper(cdm::ContentDecryptionModule_9* aCDM, WidevineDecryptor* aDecryptor); - cdm::ContentDecryptionModule_8* GetCDM() const { return mCDM; } + cdm::ContentDecryptionModule_9* GetCDM() const { return mCDM; } private: ~CDMWrapper(); - cdm::ContentDecryptionModule_8* mCDM; + cdm::ContentDecryptionModule_9* mCDM; RefPtr mDecryptor; }; diff --git a/dom/media/gmp/widevine-adapter/WidevineVideoDecoder.h b/dom/media/gmp/widevine-adapter/WidevineVideoDecoder.h index b143f75f7..f5e63519b 100644 --- a/dom/media/gmp/widevine-adapter/WidevineVideoDecoder.h +++ b/dom/media/gmp/widevine-adapter/WidevineVideoDecoder.h @@ -45,7 +45,7 @@ private: ~WidevineVideoDecoder(); - cdm::ContentDecryptionModule_8* CDM() const { + cdm::ContentDecryptionModule_9* CDM() const { // CDM should only be accessed before 'DecodingComplete'. MOZ_ASSERT(mCDMWrapper); // CDMWrapper ensure the CDM is non-null, no need to check again. -- cgit v1.2.3 From 6310310e0ae2acb88b2f83c7fb5abb806fa64dcb Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 10:41:49 -0600 Subject: [EME} Hackily implement cdm::Host_9::RequestStorageId TODO: Implement this properly in the future. --- dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp | 13 +++++++++++++ dom/media/gmp/widevine-adapter/WidevineDecryptor.h | 2 +- 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp index e85aa2db3..e3560d33f 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp @@ -541,4 +541,17 @@ WidevineDecryptor::CreateFileIO(FileIOClient* aClient) return new WidevineFileIO(aClient); } +void +WidevineDecryptor::RequestStorageId(uint32_t aVersion) +{ + Log("ChromiumCDMChild::RequestStorageId() aVersion = %u", aVersion); + if (aVersion >= 0x80000000) { + mCDM->OnStorageId(aVersion, nullptr, 0); + return; + } + + //TODO: Need to provide a menaingful buffer instead of a dummy one. + mCDM->OnStorageId(aVersion, new uint8_t[1024*1024], 1024 * 1024); +} + } // namespace mozilla diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.h b/dom/media/gmp/widevine-adapter/WidevineDecryptor.h index c1a1ebaa1..f291c321d 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.h +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.h @@ -110,7 +110,7 @@ public: cdm::Status aDecoderStatus) override; // cdm::Host_9 interface // NOTE: the interface has changed upstream. - void RequestStorageId() override {} + void RequestStorageId(uint32_t aVersion) override; cdm::FileIO* CreateFileIO(cdm::FileIOClient* aClient) override; GMPDecryptorCallback* Callback() const { return mCallback; } -- cgit v1.2.3 From 34bfc1f409b4cafa65dbc4f3087c349eb1a1dec4 Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 12:31:48 -0600 Subject: [EME] Update content_decryption_module.h to more recent revision Adds support for cdm::ContentDecryptionModule_9 and cdm::Host_9 definitions, HDCP definitions, and 10 and 12 bit image format definitions. --- dom/media/gmp/widevine-adapter/WidevineAdapter.cpp | 6 +- dom/media/gmp/widevine-adapter/WidevineUtils.cpp | 2 +- .../widevine-adapter/content_decryption_module.h | 266 +++++++++++++-------- .../content_decryption_module_export.h | 22 ++ 4 files changed, 193 insertions(+), 103 deletions(-) create mode 100644 dom/media/gmp/widevine-adapter/content_decryption_module_export.h diff --git a/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp b/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp index fa703ab0b..57d4ecec2 100644 --- a/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineAdapter.cpp @@ -106,8 +106,8 @@ WidevineAdapter::GMPGetAPI(const char* aAPIName, WidevineDecryptor* decryptor = new WidevineDecryptor(); - auto cdm = reinterpret_cast( - create(cdm::ContentDecryptionModule::kVersion, + auto cdm = reinterpret_cast( + create(cdm::ContentDecryptionModule_9::kVersion, kEMEKeySystemWidevine.get(), kEMEKeySystemWidevine.Length(), &GetCdmHost, @@ -161,7 +161,7 @@ WidevineAdapter::Supports(int32_t aModuleVersion, int32_t aHostVersion) { return aModuleVersion == CDM_MODULE_VERSION && - aInterfaceVersion == cdm::ContentDecryptionModule::kVersion && + aInterfaceVersion == cdm::ContentDecryptionModule_9::kVersion && aHostVersion == cdm::Host_9::kVersion; } diff --git a/dom/media/gmp/widevine-adapter/WidevineUtils.cpp b/dom/media/gmp/widevine-adapter/WidevineUtils.cpp index deb71e51a..10c6c2e18 100644 --- a/dom/media/gmp/widevine-adapter/WidevineUtils.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineUtils.cpp @@ -43,7 +43,7 @@ ToGMPErr(cdm::Status aStatus) case cdm::kSuccess: return GMPNoErr; case cdm::kNeedMoreData: return GMPGenericErr; case cdm::kNoKey: return GMPNoKeyErr; - case cdm::kSessionError: return GMPGenericErr; + case cdm::kInitializationError: return GMPGenericErr; case cdm::kDecryptError: return GMPCryptoErr; case cdm::kDecodeError: return GMPDecodeErr; case cdm::kDeferredInitialization: return GMPGenericErr; diff --git a/dom/media/gmp/widevine-adapter/content_decryption_module.h b/dom/media/gmp/widevine-adapter/content_decryption_module.h index 512ca9768..3f065017b 100644 --- a/dom/media/gmp/widevine-adapter/content_decryption_module.h +++ b/dom/media/gmp/widevine-adapter/content_decryption_module.h @@ -5,6 +5,8 @@ #ifndef CDM_CONTENT_DECRYPTION_MODULE_H_ #define CDM_CONTENT_DECRYPTION_MODULE_H_ +#include "content_decryption_module_export.h" + #if defined(_MSC_VER) typedef unsigned char uint8_t; typedef unsigned int uint32_t; @@ -14,25 +16,21 @@ typedef __int64 int64_t; #include #endif -// Define CDM_EXPORT so that functionality implemented by the CDM module -// can be exported to consumers. -#if defined(WIN32) - -#if defined(CDM_IMPLEMENTATION) -#define CDM_EXPORT __declspec(dllexport) -#else -#define CDM_EXPORT __declspec(dllimport) -#endif // defined(CDM_IMPLEMENTATION) - -#else // defined(WIN32) - -#if defined(CDM_IMPLEMENTATION) -#define CDM_EXPORT __attribute__((visibility("default"))) +// Define CDM_CLASS_API to export class types. We have to add visibility +// attributes to make sure virtual tables in CDM consumer and CDM implementation +// are the same. Generally, it was always a good idea, as there're no guarantees +// about that for the internal symbols, but it has only become a practical issue +// after introduction of LTO devirtualization. See more details on +// https://crbug.com/609564#c35 +#if defined(_WIN32) +#if defined(__clang__) +#define CDM_CLASS_API [[clang::lto_visibility_public]] #else -#define CDM_EXPORT +#define CDM_CLASS_API #endif - -#endif // defined(WIN32) +#else // defined(_WIN32) +#define CDM_CLASS_API __attribute__((visibility("default"))) +#endif // defined(_WIN32) // The version number must be rolled when the exported functions are updated! // If the CDM and the adapter use different versions of these functions, the @@ -48,9 +46,9 @@ typedef __int64 int64_t; #define BUILD_ENTRYPOINT_NO_EXPANSION(name, version) name##_##version extern "C" { -CDM_EXPORT void INITIALIZE_CDM_MODULE(); +CDM_API void INITIALIZE_CDM_MODULE(); -CDM_EXPORT void DeinitializeCdmModule(); +CDM_API void DeinitializeCdmModule(); // Returns a pointer to the requested CDM Host interface upon success. // Returns NULL if the requested CDM Host interface is not supported. @@ -65,30 +63,30 @@ typedef void* (*GetCdmHostFunc)(int host_interface_version, void* user_data); // |cdm_interface_version|. // Caller retains ownership of arguments and must call Destroy() on the returned // object. -CDM_EXPORT void* CreateCdmInstance( +CDM_API void* CreateCdmInstance( int cdm_interface_version, const char* key_system, uint32_t key_system_size, GetCdmHostFunc get_cdm_host_func, void* user_data); -CDM_EXPORT const char* GetCdmVersion(); +CDM_API const char* GetCdmVersion(); } namespace cdm { -class AudioFrames; -class DecryptedBlock; -class VideoFrame; +class CDM_CLASS_API AudioFrames; +class CDM_CLASS_API DecryptedBlock; +class CDM_CLASS_API VideoFrame; -class Host_7; -class Host_8; +class CDM_CLASS_API Host_8; +class CDM_CLASS_API Host_9; enum Status { kSuccess = 0, kNeedMoreData, // Decoder needs more data to produce a decoded frame/sample. - kNoKey, // The required decryption key is not available. - kSessionError, // Session management error. - kDecryptError, // Decryption failed. - kDecodeError, // Error decoding audio or video. + kNoKey, // The required decryption key is not available. + kInitializationError, // Initialization error. + kDecryptError, // Decryption failed. + kDecodeError, // Error decoding audio or video. kDeferredInitialization // Decoder is not ready for initialization. }; @@ -97,6 +95,7 @@ enum Status { // The following starts with the list of DOM4 exceptions from: // http://www.w3.org/TR/dom/#domexception // Some DOM4 exceptions are not included as they are not expected to be used. +// Should only be used on Host_8 and before. enum Error { kNotSupportedError = 9, kInvalidStateError = 11, @@ -113,8 +112,20 @@ enum Error { kOutputError = 101 }; -// Time is defined as the number of seconds since the -// Epoch (00:00:00 UTC, January 1, 1970). +// Exceptions used by the CDM to reject promises. +// https://w3c.github.io/encrypted-media/#exceptions +enum Exception { + kExceptionTypeError, + kExceptionNotSupportedError, + kExceptionInvalidStateError, + kExceptionQuotaExceededError +}; + +// Time is defined as the number of seconds since the Epoch +// (00:00:00 UTC, January 1, 1970), not including any added leap second. +// Also see Time definition in spec: https://w3c.github.io/encrypted-media/#time +// Note that Time is defined in millisecond accuracy in the spec but in second +// accuracy here. typedef double Time; // An input buffer can be split into several continuous subsamples. @@ -151,13 +162,13 @@ struct SubsampleEntry { // unencrypted. struct InputBuffer { InputBuffer() - : data(NULL), + : data(nullptr), data_size(0), - key_id(NULL), + key_id(nullptr), key_id_size(0), - iv(NULL), + iv(nullptr), iv_size(0), - subsamples(NULL), + subsamples(nullptr), num_subsamples(0), timestamp(0) {} @@ -188,7 +199,7 @@ struct AudioDecoderConfig { channel_count(0), bits_per_channel(0), samples_per_second(0), - extra_data(NULL), + extra_data(nullptr), extra_data_size(0) {} AudioCodec codec; @@ -214,10 +225,25 @@ enum AudioFormat { }; // Surface formats based on FOURCC labels, see: http://www.fourcc.org/yuv.php +// Values are chosen to be consistent with Chromium's VideoPixelFormat values. enum VideoFormat { kUnknownVideoFormat = 0, // Unknown format value. Used for error reporting. - kYv12, // 12bpp YVU planar 1x1 Y, 2x2 VU samples. - kI420 // 12bpp YVU planar 1x1 Y, 2x2 UV samples. + kYv12 = 1, // 12bpp YVU planar 1x1 Y, 2x2 VU samples. + kI420 = 2, // 12bpp YUV planar 1x1 Y, 2x2 UV samples. + + // In the following formats, each sample uses 16-bit in storage, while the + // sample value is stored in the least significant N bits where N is + // specified by the number after "P". For example, for YUV420P9, each Y, U, + // and V sample is stored in the least significant 9 bits in a 2-byte block. + kYUV420P9 = 16, + kYUV420P10 = 17, + kYUV422P9 = 18, + kYUV422P10 = 19, + kYUV444P9 = 20, + kYUV444P10 = 21, + kYUV420P12 = 22, + kYUV422P12 = 23, + kYUV444P12 = 24, }; struct Size { @@ -245,14 +271,19 @@ struct VideoDecoderConfig { kH264ProfileHigh, kH264ProfileHigh10, kH264ProfileHigh422, - kH264ProfileHigh444Predictive + kH264ProfileHigh444Predictive, + // VP9 Profiles are only passed in starting from CDM_9. + kVP9Profile0, + kVP9Profile1, + kVP9Profile2, + kVP9Profile3 }; VideoDecoderConfig() : codec(kUnknownVideoCodec), profile(kUnknownVideoCodecProfile), format(kUnknownVideoFormat), - extra_data(NULL), + extra_data(nullptr), extra_data_size(0) {} VideoCodec codec; @@ -294,7 +325,7 @@ struct PlatformChallengeResponse { // Used when passing arrays of binary data. Does not own the referenced data. struct BinaryData { - BinaryData() : data(NULL), length(0) {} + BinaryData() : data(nullptr), length(0) {} const uint8_t* data; uint32_t length; }; @@ -316,7 +347,10 @@ enum KeyStatus { // should be 0 when |status| == kUsable. struct KeyInformation { KeyInformation() - : key_id(NULL), key_id_size(0), status(kInternalError), system_code(0) {} + : key_id(nullptr), + key_id_size(0), + status(kInternalError), + system_code(0) {} const uint8_t* key_id; uint32_t key_id_size; KeyStatus status; @@ -372,6 +406,24 @@ enum MessageType { kLicenseRelease = 2 }; +enum HdcpVersion { + kHdcpVersionNone, + kHdcpVersion1_0, + kHdcpVersion1_1, + kHdcpVersion1_2, + kHdcpVersion1_3, + kHdcpVersion1_4, + kHdcpVersion2_0, + kHdcpVersion2_1, + kHdcpVersion2_2 +}; + +struct Policy { + Policy() : min_hdcp_version(kHdcpVersionNone) {} + + HdcpVersion min_hdcp_version; +}; + // FileIO interface provides a way for the CDM to store data in a file in // persistent storage. This interface aims only at providing basic read/write // capabilities and should not be used as a full fledged file IO API. @@ -381,7 +433,7 @@ enum MessageType { // Note to implementors of this interface: // Per-origin storage and the ability for users to clear it are important. // See http://www.w3.org/TR/encrypted-media/#privacy-storedinfo. -class FileIO { +class CDM_CLASS_API FileIO { public: // Opens the file with |file_name| for read and write. // FileIOClient::OnOpenComplete() will be called after the opening @@ -421,7 +473,7 @@ class FileIO { // When kError is returned, the FileIO object could be in an error state. All // following calls (other than Close()) could return kError. The CDM should // still call Close() to destroy the FileIO object. -class FileIOClient { +class CDM_CLASS_API FileIOClient { public: enum Status { kSuccess = 0, @@ -462,10 +514,20 @@ class FileIOClient { // provided in CreateCdmInstance() to allocate any Buffer that needs to // be passed back to the caller. Implementations must call Buffer::Destroy() // when a Buffer is created that will never be returned to the caller. -class ContentDecryptionModule_7 { +class CDM_CLASS_API ContentDecryptionModule_8 { public: - static const int kVersion = 7; - typedef Host_7 Host; + static const int kVersion = 8; + typedef Host_8 Host; + + // Initializes the CDM instance, providing information about permitted + // functionalities. + // If |allow_distinctive_identifier| is false, messages from the CDM, + // such as message events, must not contain a Distinctive Identifier, + // even in an encrypted form. + // If |allow_persistent_state| is false, the CDM must not attempt to + // persist state. Calls to CreateFileIO() will fail. + virtual void Initialize(bool allow_distinctive_identifier, + bool allow_persistent_state) = 0; // SetServerCertificate(), CreateSessionAndGenerateRequest(), LoadSession(), // UpdateSession(), CloseSession(), and RemoveSession() all accept a @@ -484,8 +546,7 @@ class ContentDecryptionModule_7 { // or Host::OnRejectPromise(). virtual void CreateSessionAndGenerateRequest(uint32_t promise_id, SessionType session_type, - const char* init_data_type, - uint32_t init_data_type_size, + InitDataType init_data_type, const uint8_t* init_data, uint32_t init_data_size) = 0; @@ -631,8 +692,8 @@ class ContentDecryptionModule_7 { virtual void Destroy() = 0; protected: - ContentDecryptionModule_7() {} - virtual ~ContentDecryptionModule_7() {} + ContentDecryptionModule_8() {} + virtual ~ContentDecryptionModule_8() {} }; // ContentDecryptionModule interface that all CDMs need to implement. @@ -641,10 +702,10 @@ class ContentDecryptionModule_7 { // provided in CreateCdmInstance() to allocate any Buffer that needs to // be passed back to the caller. Implementations must call Buffer::Destroy() // when a Buffer is created that will never be returned to the caller. -class ContentDecryptionModule_8 { +class CDM_CLASS_API ContentDecryptionModule_9 { public: - static const int kVersion = 8; - typedef Host_8 Host; + static const int kVersion = 9; + typedef Host_9 Host; // Initializes the CDM instance, providing information about permitted // functionalities. @@ -656,6 +717,13 @@ class ContentDecryptionModule_8 { virtual void Initialize(bool allow_distinctive_identifier, bool allow_persistent_state) = 0; + // Gets the key status if the CDM has a hypothetical key with the |policy|. + // The CDM must respond by calling either Host::OnResolveKeyStatusPromise() + // with the result key status or Host::OnRejectPromise() if an unexpected + // error happened or this method is not supported. + virtual void GetStatusForPolicy(uint32_t promise_id, + const Policy& policy) = 0; + // SetServerCertificate(), CreateSessionAndGenerateRequest(), LoadSession(), // UpdateSession(), CloseSession(), and RemoveSession() all accept a // |promise_id|, which must be passed to the completion Host method @@ -815,18 +883,23 @@ class ContentDecryptionModule_8 { uint32_t link_mask, uint32_t output_protection_mask) = 0; + // Called by the host after a call to Host::RequestStorageId(). If the storage + // ID is not available, null/zero will be provided. + virtual void OnStorageId(const uint8_t* storage_id, + uint32_t storage_id_size) = 0; + // Destroys the object in the same context as it was created. virtual void Destroy() = 0; protected: - ContentDecryptionModule_8() {} - virtual ~ContentDecryptionModule_8() {} + ContentDecryptionModule_9() {} + virtual ~ContentDecryptionModule_9() {} }; -typedef ContentDecryptionModule_8 ContentDecryptionModule; +typedef ContentDecryptionModule_9 ContentDecryptionModule; // Represents a buffer created by Allocator implementations. -class Buffer { +class CDM_CLASS_API Buffer { public: // Destroys the buffer in the same context as it was created. virtual void Destroy() = 0; @@ -845,9 +918,9 @@ class Buffer { void operator=(const Buffer&); }; -class Host_7 { +class CDM_CLASS_API Host_8 { public: - static const int kVersion = 7; + static const int kVersion = 8; // Returns a Buffer* containing non-zero members upon success, or NULL on // failure. The caller owns the Buffer* after this call. The buffer is not @@ -859,7 +932,7 @@ class Host_7 { // from now with |context|. virtual void SetTimer(int64_t delay_ms, void* context) = 0; - // Returns the current wall time in seconds. + // Returns the current wall time. virtual Time GetCurrentWallTime() = 0; // Called by the CDM when a session is created or loaded and the value for the @@ -917,8 +990,10 @@ class Host_7 { // session |session_id|. This can happen as the result of an Update() call // or some other event. If this happens as a result of a call to Update(), // it must be called before resolving the Update() promise. |new_expiry_time| - // can be 0 to represent "undefined". Size parameter should not include - // null termination. + // represents the time after which the key(s) in the session will no longer + // be usable for decryption. It can be 0 if no such time exists or if the + // license explicitly never expires. Size parameter should not include null + // termination. virtual void OnExpirationChange(const char* session_id, uint32_t session_id_size, Time new_expiry_time) = 0; @@ -978,13 +1053,13 @@ class Host_7 { virtual FileIO* CreateFileIO(FileIOClient* client) = 0; protected: - Host_7() {} - virtual ~Host_7() {} + Host_8() {} + virtual ~Host_8() {} }; -class Host_8 { +class CDM_CLASS_API Host_9 { public: - static const int kVersion = 8; + static const int kVersion = 9; // Returns a Buffer* containing non-zero members upon success, or NULL on // failure. The caller owns the Buffer* after this call. The buffer is not @@ -996,9 +1071,14 @@ class Host_8 { // from now with |context|. virtual void SetTimer(int64_t delay_ms, void* context) = 0; - // Returns the current wall time in seconds. + // Returns the current wall time. virtual Time GetCurrentWallTime() = 0; + // Called by the CDM when a key status is available in response to + // GetStatusForPolicy(). + virtual void OnResolveKeyStatusPromise(uint32_t promise_id, + KeyStatus key_status) = 0; + // Called by the CDM when a session is created or loaded and the value for the // MediaKeySession's sessionId attribute is available (|session_id|). // This must be called before OnSessionMessage() or @@ -1016,26 +1096,21 @@ class Host_8 { // Called by the CDM when an error occurs as a result of one of the // ContentDecryptionModule calls that accept a |promise_id|. - // |error| must be specified, |error_message| and |system_code| + // |exception| must be specified. |error_message| and |system_code| // are optional. |error_message_size| should not include null termination. virtual void OnRejectPromise(uint32_t promise_id, - Error error, + Exception exception, uint32_t system_code, const char* error_message, uint32_t error_message_size) = 0; // Called by the CDM when it has a message for session |session_id|. // Size parameters should not include null termination. - // |legacy_destination_url| is only for supporting the prefixed EME API and - // is ignored by unprefixed EME. It should only be non-null if |message_type| - // is kLicenseRenewal. virtual void OnSessionMessage(const char* session_id, uint32_t session_id_size, MessageType message_type, const char* message, - uint32_t message_size, - const char* legacy_destination_url, - uint32_t legacy_destination_url_length) = 0; + uint32_t message_size) = 0; // Called by the CDM when there has been a change in keys or their status for // session |session_id|. |has_additional_usable_key| should be set if a @@ -1054,8 +1129,10 @@ class Host_8 { // session |session_id|. This can happen as the result of an Update() call // or some other event. If this happens as a result of a call to Update(), // it must be called before resolving the Update() promise. |new_expiry_time| - // can be 0 to represent "undefined". Size parameter should not include - // null termination. + // represents the time after which the key(s) in the session will no longer + // be usable for decryption. It can be 0 if no such time exists or if the + // license explicitly never expires. Size parameter should not include null + // termination. virtual void OnExpirationChange(const char* session_id, uint32_t session_id_size, Time new_expiry_time) = 0; @@ -1065,21 +1142,6 @@ class Host_8 { virtual void OnSessionClosed(const char* session_id, uint32_t session_id_size) = 0; - // Called by the CDM when an error occurs in session |session_id| - // unrelated to one of the ContentDecryptionModule calls that accept a - // |promise_id|. |error| must be specified, |error_message| and - // |system_code| are optional. Length parameters should not include null - // termination. - // Note: - // - This method is only for supporting prefixed EME API. - // - This method will be ignored by unprefixed EME. All errors reported - // in this method should probably also be reported by one of other methods. - virtual void OnLegacySessionError( - const char* session_id, uint32_t session_id_length, - Error error, - uint32_t system_code, - const char* error_message, uint32_t error_message_length) = 0; - // The following are optional methods that may not be implemented on all // platforms. @@ -1114,13 +1176,19 @@ class Host_8 { // CDM can call this method multiple times to operate on different files. virtual FileIO* CreateFileIO(FileIOClient* client) = 0; + // Requests the storage ID. The ID will be returned by the host via + // ContentDecryptionModule::OnStorageId(). A storage ID is a stable, device + // specific ID used by the CDM to securely store persistent data. The CDM must + // not expose the ID outside the client device, even in encrypted form. + virtual void RequestStorageId() = 0; + protected: - Host_8() {} - virtual ~Host_8() {} + Host_9() {} + virtual ~Host_9() {} }; // Represents a decrypted block that has not been decoded. -class DecryptedBlock { +class CDM_CLASS_API DecryptedBlock { public: virtual void SetDecryptedBuffer(Buffer* buffer) = 0; virtual Buffer* DecryptedBuffer() = 0; @@ -1135,7 +1203,7 @@ class DecryptedBlock { virtual ~DecryptedBlock() {} }; -class VideoFrame { +class CDM_CLASS_API VideoFrame { public: enum VideoPlane { kYPlane = 0, @@ -1178,7 +1246,7 @@ class VideoFrame { // // |<----------------- AudioFrames ------------------>| // | audio buffer 0 | audio buffer 1 | audio buffer 2 | -class AudioFrames { +class CDM_CLASS_API AudioFrames { public: virtual void SetFrameBuffer(Buffer* buffer) = 0; virtual Buffer* FrameBuffer() = 0; diff --git a/dom/media/gmp/widevine-adapter/content_decryption_module_export.h b/dom/media/gmp/widevine-adapter/content_decryption_module_export.h new file mode 100644 index 000000000..51d485892 --- /dev/null +++ b/dom/media/gmp/widevine-adapter/content_decryption_module_export.h @@ -0,0 +1,22 @@ +// Copyright 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CDM_CONTENT_DECRYPTION_MODULE_EXPORT_H_ +#define CDM_CONTENT_DECRYPTION_MODULE_EXPORT_H_ + +// Define CDM_API so that functionality implemented by the CDM module +// can be exported to consumers. +#if defined(_WIN32) + +#if defined(CDM_IMPLEMENTATION) +#define CDM_API __declspec(dllexport) +#else +#define CDM_API __declspec(dllimport) +#endif // defined(CDM_IMPLEMENTATION) + +#else // defined(_WIN32) +#define CDM_API __attribute__((visibility("default"))) +#endif // defined(_WIN32) + +#endif // CDM_CONTENT_DECRYPTION_MODULE_EXPORT_H_ -- cgit v1.2.3 From 8279f15d49dc14ec158c6457fd266adc1bfbb12e Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 13:48:02 -0600 Subject: [EME] Add content_decryption_module_ext.h --- .../content_decryption_module_ext.h | 64 ++++++++++++++++++++++ 1 file changed, 64 insertions(+) create mode 100644 dom/media/gmp/widevine-adapter/content_decryption_module_ext.h diff --git a/dom/media/gmp/widevine-adapter/content_decryption_module_ext.h b/dom/media/gmp/widevine-adapter/content_decryption_module_ext.h new file mode 100644 index 000000000..5df8344e6 --- /dev/null +++ b/dom/media/gmp/widevine-adapter/content_decryption_module_ext.h @@ -0,0 +1,64 @@ +// Copyright 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CDM_CONTENT_DECRYPTION_MODULE_EXT_H_ +#define CDM_CONTENT_DECRYPTION_MODULE_EXT_H_ + +#if defined(_WIN32) +#include +#endif + +#include "content_decryption_module_export.h" + +#if defined(_MSC_VER) +typedef unsigned int uint32_t; +#else +#include +#endif + +namespace cdm { + +#if defined(_WIN32) +typedef wchar_t FilePathCharType; +typedef HANDLE PlatformFile; +const PlatformFile kInvalidPlatformFile = INVALID_HANDLE_VALUE; +#else +typedef char FilePathCharType; +typedef int PlatformFile; +const PlatformFile kInvalidPlatformFile = -1; +#endif // defined(_WIN32) + +struct HostFile { + HostFile(const FilePathCharType* file_path, + PlatformFile file, + PlatformFile sig_file) + : file_path(file_path), file(file), sig_file(sig_file) {} + + // File that is part of the host of the CDM. + const FilePathCharType* file_path = nullptr; + PlatformFile file = kInvalidPlatformFile; + + // Signature file for |file|. + PlatformFile sig_file = kInvalidPlatformFile; +}; + +} // namespace cdm + +extern "C" { + +// Functions in this file are dynamically retrieved by their versioned function +// names. Increment the version number for any backward incompatible API +// changes. + +// Verifies CDM host. All files in |host_files| are opened in read-only mode. +// +// Returns false and closes all files if there is an immediate failure. +// Otherwise returns true as soon as possible and processes the files +// asynchronously. All files MUST be closed by the CDM after this one-time +// processing is finished. +CDM_API bool VerifyCdmHost_0(const cdm::HostFile* host_files, + uint32_t num_files); +} + +#endif // CDM_CONTENT_DECRYPTION_MODULE_EXT_H_ -- cgit v1.2.3 From e1d7634ba00b11292c742a6d8e03df111149d7c9 Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 13:50:27 -0600 Subject: [EME] Cherry-pick fix for content_decryption_module.h Fixes build bustage with GCC/clang. --- .../widevine-adapter/content_decryption_module.h | 39 ++++++++++++++-------- 1 file changed, 25 insertions(+), 14 deletions(-) diff --git a/dom/media/gmp/widevine-adapter/content_decryption_module.h b/dom/media/gmp/widevine-adapter/content_decryption_module.h index 3f065017b..0539135fb 100644 --- a/dom/media/gmp/widevine-adapter/content_decryption_module.h +++ b/dom/media/gmp/widevine-adapter/content_decryption_module.h @@ -441,8 +441,9 @@ class CDM_CLASS_API FileIO { // - When the file is opened by a CDM instance, it will be classified as "in // use". In this case other CDM instances in the same domain may receive // kInUse status when trying to open it. - // - |file_name| must not contain forward slash ('/') or backslash ('\'), and - // must not start with an underscore ('_'). + // - |file_name| must only contain letters (A-Za-z), digits(0-9), or "._-". + // It must not start with an underscore ('_'), and must be at least 1 + // character and no more than 256 characters long. virtual void Open(const char* file_name, uint32_t file_name_size) = 0; // Reads the contents of the file. FileIOClient::OnReadComplete() will be @@ -799,8 +800,8 @@ class CDM_CLASS_API ContentDecryptionModule_9 { // // Returns kSuccess if the |audio_decoder_config| is supported and the CDM // audio decoder is successfully initialized. - // Returns kSessionError if |audio_decoder_config| is not supported. The CDM - // may still be able to do Decrypt(). + // Returns kInitializationError if |audio_decoder_config| is not supported. + // The CDM may still be able to do Decrypt(). // Returns kDeferredInitialization if the CDM is not ready to initialize the // decoder at this time. Must call Host::OnDeferredInitializationDone() once // initialization is complete. @@ -812,8 +813,8 @@ class CDM_CLASS_API ContentDecryptionModule_9 { // // Returns kSuccess if the |video_decoder_config| is supported and the CDM // video decoder is successfully initialized. - // Returns kSessionError if |video_decoder_config| is not supported. The CDM - // may still be able to do Decrypt(). + // Returns kInitializationError if |video_decoder_config| is not supported. + // The CDM may still be able to do Decrypt(). // Returns kDeferredInitialization if the CDM is not ready to initialize the // decoder at this time. Must call Host::OnDeferredInitializationDone() once // initialization is complete. @@ -883,9 +884,16 @@ class CDM_CLASS_API ContentDecryptionModule_9 { uint32_t link_mask, uint32_t output_protection_mask) = 0; - // Called by the host after a call to Host::RequestStorageId(). If the storage - // ID is not available, null/zero will be provided. - virtual void OnStorageId(const uint8_t* storage_id, + // Called by the host after a call to Host::RequestStorageId(). If the + // version of the storage ID requested is available, |storage_id| and + // |storage_id_size| are set appropriately. |version| will be the same as + // what was requested, unless 0 (latest) was requested, in which case + // |version| will be the actual version number for the |storage_id| returned. + // If the requested version is not available, null/zero will be provided as + // |storage_id| and |storage_id_size|, respectively, and |version| should be + // ignored. + virtual void OnStorageId(uint32_t version, + const uint8_t* storage_id, uint32_t storage_id_size) = 0; // Destroys the object in the same context as it was created. @@ -1176,11 +1184,14 @@ class CDM_CLASS_API Host_9 { // CDM can call this method multiple times to operate on different files. virtual FileIO* CreateFileIO(FileIOClient* client) = 0; - // Requests the storage ID. The ID will be returned by the host via - // ContentDecryptionModule::OnStorageId(). A storage ID is a stable, device - // specific ID used by the CDM to securely store persistent data. The CDM must - // not expose the ID outside the client device, even in encrypted form. - virtual void RequestStorageId() = 0; + // Requests a specific version of the storage ID. A storage ID is a stable, + // device specific ID used by the CDM to securely store persistent data. The + // ID will be returned by the host via ContentDecryptionModule::OnStorageId(). + // If |version| is 0, the latest version will be returned. All |version|s + // that are greater than or equal to 0x80000000 are reserved for the CDM and + // should not be supported or returned by the host. The CDM must not expose + // the ID outside the client device, even in encrypted form. + virtual void RequestStorageId(uint32_t version) = 0; protected: Host_9() {} -- cgit v1.2.3 From 3a6a37ca1b335dc97247f7facae46bc026802e03 Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 13:55:14 -0600 Subject: Style fixes --- dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp index e3560d33f..ab62ba7ef 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp @@ -359,10 +359,10 @@ ConvertCDMErrorToCDMException(cdm::Error error) { void WidevineDecryptor::OnRejectPromise(uint32_t aPromiseId, - cdm::Exception aException, - uint32_t aSystemCode, - const char* aErrorMessage, - uint32_t aErrorMessageSize) + cdm::Exception aException, + uint32_t aSystemCode, + const char* aErrorMessage, + uint32_t aErrorMessageSize) { if (!mCallback) { Log("Decryptor::OnRejectPromise(aPromiseId=%d, err=%d, sysCode=%u, msg=%s) FAIL; !mCallback", @@ -390,10 +390,10 @@ ToGMPMessageType(MessageType message_type) void WidevineDecryptor::OnSessionMessage(const char* aSessionId, - uint32_t aSessionIdSize, - cdm::MessageType aMessageType, - const char* aMessage, - uint32_t aMessageSize) + uint32_t aSessionIdSize, + cdm::MessageType aMessageType, + const char* aMessage, + uint32_t aMessageSize) { if (!mCallback) { Log("Decryptor::OnSessionMessage() FAIL; !mCallback"); @@ -544,7 +544,7 @@ WidevineDecryptor::CreateFileIO(FileIOClient* aClient) void WidevineDecryptor::RequestStorageId(uint32_t aVersion) { - Log("ChromiumCDMChild::RequestStorageId() aVersion = %u", aVersion); + Log("Decryptor::RequestStorageId() aVersion = %u", aVersion); if (aVersion >= 0x80000000) { mCDM->OnStorageId(aVersion, nullptr, 0); return; -- cgit v1.2.3 From 05a51611bc15f436adac30ea7097a48bb7c7b51e Mon Sep 17 00:00:00 2001 From: trav90 Date: Fri, 8 Feb 2019 14:40:12 -0600 Subject: Build bustage fixes --- dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp index ab62ba7ef..150480644 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp @@ -302,7 +302,7 @@ WidevineDecryptor::GetCurrentWallTime() } void -ChromiumCDMChild::OnResolveKeyStatusPromise(uint32_t aPromiseId, +WidevineDecryptor::OnResolveKeyStatusPromise(uint32_t aPromiseId, cdm::KeyStatus aKeyStatus) { //TODO: The callback of GetStatusForPolicy. See Mozilla bug 1404230. } @@ -351,6 +351,10 @@ ConvertCDMErrorToCDMException(cdm::Error error) { return cdm::Exception::kExceptionTypeError; case cdm::kQuotaExceededError: return cdm::Exception::kExceptionQuotaExceededError; + + case cdm::kUnknownError: + case cdm::kClientError: + case cdm::kOutputError: break; } @@ -370,7 +374,7 @@ WidevineDecryptor::OnRejectPromise(uint32_t aPromiseId, return; } Log("Decryptor::OnRejectPromise(aPromiseId=%d, err=%d, sysCode=%u, msg=%s)", - aPromiseId, (int)aError, aSystemCode, aErrorMessage); + aPromiseId, (int)aException, aSystemCode, aErrorMessage); mCallback->RejectPromise(aPromiseId, ToGMPDOMException(aException), !aErrorMessageSize ? "" : aErrorMessage, -- cgit v1.2.3 From cece1cb715b43fd99ec3dda926abe30181a8f5dd Mon Sep 17 00:00:00 2001 From: trav90 Date: Sat, 9 Feb 2019 07:50:35 -0600 Subject: [EME] Remove WidevineDecryptor::OnLegacySessionError Not needed for more recent CDM versions. --- .../gmp/widevine-adapter/WidevineDecryptor.cpp | 22 ---------------------- 1 file changed, 22 deletions(-) diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp index 150480644..f89888a72 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp @@ -485,28 +485,6 @@ WidevineDecryptor::OnSessionClosed(const char* aSessionId, mCallback->SessionClosed(aSessionId, aSessionIdSize); } -void -WidevineDecryptor::OnLegacySessionError(const char* aSessionId, - uint32_t aSessionIdLength, - Error aError, - uint32_t aSystemCode, - const char* aErrorMessage, - uint32_t aErrorMessageLength) -{ - if (!mCallback) { - Log("Decryptor::OnLegacySessionError(sid=%s, error=%d) FAIL; !mCallback", - aSessionId, (int)aError); - return; - } - Log("Decryptor::OnLegacySessionError(sid=%s, error=%d)", aSessionId, (int)aError); - mCallback->SessionError(aSessionId, - aSessionIdLength, - ToGMPDOMException(aError), - aSystemCode, - aErrorMessage, - aErrorMessageLength); -} - void WidevineDecryptor::SendPlatformChallenge(const char* aServiceId, uint32_t aServiceIdSize, -- cgit v1.2.3 From acfc69ec7e3470f8682e655af289a254a1c01a2d Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 18:15:07 +0200 Subject: Support string default values for unions containing USVString --- dom/bindings/Codegen.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index cb93e4897..5c4aa746d 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4355,7 +4355,9 @@ def handleDefaultStringValue(defaultValue, method): passing as the second argument of handleDefault; in particular it does not end with a ';' """ - assert defaultValue.type.isDOMString() or defaultValue.type.isByteString() + assert (defaultValue.type.isDOMString() or + defaultValue.type.isUSVString() or + defaultValue.type.isByteString()) return ("static const %(char_t)s data[] = { %(data)s };\n" "%(method)s(data, ArrayLength(data) - 1)") % { 'char_t': "char" if defaultValue.type.isByteString() else "char16_t", -- cgit v1.2.3 From bcdacfe2dfb9c9e36de462182562ebf4eec94f36 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 18:25:55 +0200 Subject: Add a ClearElementAt API to nsTArray --- xpcom/glue/nsTArray.h | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/xpcom/glue/nsTArray.h b/xpcom/glue/nsTArray.h index 82586a79a..64af17bbb 100644 --- a/xpcom/glue/nsTArray.h +++ b/xpcom/glue/nsTArray.h @@ -1503,6 +1503,24 @@ public: mozilla::Forward(aItem)); } + // Reconstruct the element at the given index, and return a pointer to the + // reconstructed element. This will destroy the existing element and + // default-construct a new one, giving you a state much like what single-arg + // InsertElementAt(), or no-arg AppendElement() does, but without changing the + // length of the array. + // + // array[idx] = T() + // + // would accomplish the same thing as long as T has the appropriate moving + // operator=, but some types don't for various reasons. + elem_type* ReconstructElementAt(index_type aIndex) + { + elem_type* elem = &ElementAt(aIndex); + elem_traits::Destruct(elem); + elem_traits::Construct(elem); + return elem; + } + // This method searches for the smallest index of an element that is strictly // greater than |aItem|. If |aItem| is inserted at this index, the array will // remain sorted and |aItem| would come after all elements that are equal to -- cgit v1.2.3 From 5a10462a92197769cc7af04287c6315fa8961dcd Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 18:46:01 +0200 Subject: Change the MozMap API and data storage to more what we want record<> to look like --- dom/bindings/BindingUtils.h | 16 +++------ dom/bindings/Codegen.py | 51 +++++++++++++-------------- dom/bindings/MozMap.h | 82 +++++++++++-------------------------------- dom/fetch/InternalHeaders.cpp | 9 ++--- 4 files changed, 55 insertions(+), 103 deletions(-) diff --git a/dom/bindings/BindingUtils.h b/dom/bindings/BindingUtils.h index 24b47a545..23bbbea5a 100644 --- a/dom/bindings/BindingUtils.h +++ b/dom/bindings/BindingUtils.h @@ -2293,19 +2293,13 @@ public: } }; -template -static void -TraceMozMapValue(T* aValue, void* aClosure) -{ - JSTracer* trc = static_cast(aClosure); - // Act like it's a one-element sequence to leverage all that infrastructure. - SequenceTracer::TraceSequence(trc, aValue, aValue + 1); -} - template void TraceMozMap(JSTracer* trc, MozMap& map) { - map.EnumerateValues(TraceMozMapValue, trc); + for (auto& entry : map.Entries()) { + // Act like it's a one-element sequence to leverage all that infrastructure. + SequenceTracer::TraceSequence(trc, &entry.mValue, &entry.mValue + 1); + } } // sequence @@ -2317,7 +2311,7 @@ class SequenceTracer, false, false, false> public: static void TraceSequence(JSTracer* trc, MozMap* seqp, MozMap* end) { for (; seqp != end; ++seqp) { - seqp->EnumerateValues(TraceMozMapValue, trc); + TraceMozMap(trc, *seqp); } } }; diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index 5c4aa746d..fd811bb3a 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4774,20 +4774,21 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, templateBody = fill( """ - ${mozMapType} &mozMap = ${mozMapRef}; + auto& mozMapEntries = ${mozMapRef}.Entries(); JS::Rooted mozMapObj(cx, &$${val}.toObject()); JS::Rooted ids(cx, JS::IdVector(cx)); if (!JS_Enumerate(cx, mozMapObj, &ids)) { $*{exceptionCode} } + if (!mozMapEntries.SetCapacity(ids.length(), mozilla::fallible)) { + JS_ReportOutOfMemory(cx); + $*{exceptionCode} + } JS::Rooted propNameValue(cx); JS::Rooted temp(cx); JS::Rooted curId(cx); for (size_t i = 0; i < ids.length(); ++i) { - // Make sure we get the value before converting the name, since - // getting the value can trigger GC but our name is a dependent - // string. curId = ids[i]; binding_detail::FakeString propName; bool isSymbol; @@ -4799,18 +4800,17 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, continue; } - ${valueType}* slotPtr = mozMap.AddEntry(propName); - if (!slotPtr) { - JS_ReportOutOfMemory(cx); - $*{exceptionCode} - } - ${valueType}& slot = *slotPtr; + // Safe to do an infallible append here, because we did a + // SetCapacity above to the right capacity. + ${mozMapType}::EntryType* entry = mozMapEntries.AppendElement(); + entry->mKey = propName; + ${valueType}& slot = entry->mValue; $*{valueConversion} } """, exceptionCode=exceptionCode, - mozMapType=mozMapType, mozMapRef=mozMapRef, + mozMapType=mozMapType, valueType=valueInfo.declType.define(), valueConversion=valueConversion) @@ -6460,8 +6460,6 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, code = fill( """ - nsTArray keys; - ${result}.GetKeys(keys); JS::Rooted returnObj(cx, JS_NewPlainObject(cx)); if (!returnObj) { $*{exceptionCode} @@ -6469,15 +6467,16 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, // Scope for 'tmp' { JS::Rooted tmp(cx); - for (size_t idx = 0; idx < keys.Length(); ++idx) { - auto& ${valueName} = ${result}.Get(keys[idx]); + for (auto& entry : ${result}.Entries()) { + auto& ${valueName} = entry.mValue; // Control block to let us common up the JS_DefineUCProperty calls when there // are different ways to succeed at wrapping the value. do { $*{innerTemplate} } while (0); - if (!JS_DefineUCProperty(cx, returnObj, keys[idx].get(), - keys[idx].Length(), tmp, + if (!JS_DefineUCProperty(cx, returnObj, + entry.mKey.BeginReading(), + entry.mKey.Length(), tmp, JSPROP_ENUMERATE)) { $*{exceptionCode} } @@ -7202,28 +7201,26 @@ def wrapTypeIntoCurrentCompartment(type, value, isMember=True): return wrapCode if type.isMozMap(): - origValue = value origType = type if type.nullable(): type = type.inner - value = "%s.Value()" % value + mozMapRef = "%s.Value()" % value + else: + mozMapRef = value global mapWrapLevel - key = "mapName%d" % mapWrapLevel + entryRef = "mapEntry%d" % mapWrapLevel mapWrapLevel += 1 wrapElement = wrapTypeIntoCurrentCompartment(type.inner, - "%s.Get(%sKeys[%sIndex])" % (value, key, key)) + "%s.mValue" % entryRef) mapWrapLevel -= 1 if not wrapElement: return None wrapCode = CGWrapper(CGIndenter(wrapElement), - pre=(""" - nsTArray %sKeys; - %s.GetKeys(%sKeys); - for (uint32_t %sIndex = 0; %sIndex < %sKeys.Length(); ++%sIndex) { - """ % (key, value, key, key, key, key, key)), + pre=("for (auto& %s : %s.Entries()) {\n" % + (entryRef, mozMapRef)), post="}\n") if origType.nullable(): - wrapCode = CGIfWrapper(wrapCode, "!%s.IsNull()" % origValue) + wrapCode = CGIfWrapper(wrapCode, "!%s.IsNull()" % value) return wrapCode if type.isDictionary(): diff --git a/dom/bindings/MozMap.h b/dom/bindings/MozMap.h index 1e920c098..2725c74ff 100644 --- a/dom/bindings/MozMap.h +++ b/dom/bindings/MozMap.h @@ -5,9 +5,7 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ /** - * Class for representing MozMap arguments. This is an nsTHashtable - * under the hood, but we don't want to leak that implementation - * detail. + * Class for representing MozMap arguments. Basically an array under the hood. */ #ifndef mozilla_dom_MozMap_h @@ -24,34 +22,34 @@ namespace mozilla { namespace dom { namespace binding_detail { -template -class MozMapEntry : public nsStringHashKey +template +class MozMapEntry { public: - explicit MozMapEntry(const nsAString* aKeyTypePointer) - : nsStringHashKey(aKeyTypePointer) + MozMapEntry() { } // Move constructor so we can do MozMaps of MozMaps. - MozMapEntry(MozMapEntry&& aOther) - : nsStringHashKey(aOther), - mData(Move(aOther.mData)) + MozMapEntry(MozMapEntry&& aOther) + : mKey(Move(aOther.mKey)), + mValue(Move(aOther.mValue)) { } - DataType mData; + KeyType mKey; + ValueType mValue; }; } // namespace binding_detail -template -class MozMap : protected nsTHashtable> +template +class MozMap { public: - typedef typename binding_detail::MozMapEntry EntryType; - typedef nsTHashtable Base; - typedef MozMap SelfType; + typedef nsString KeyType; + typedef typename binding_detail::MozMapEntry EntryType; + typedef MozMap SelfType; MozMap() { @@ -59,60 +57,22 @@ public: // Move constructor so we can do MozMap of MozMap. MozMap(SelfType&& aOther) : - Base(Move(aOther)) + mEntries(Move(aOther.mEntries)) { } - // The return value is only safe to use until an AddEntry call. - const DataType& Get(const nsAString& aKey) const + const nsTArray& Entries() const { - const EntryType* ent = this->GetEntry(aKey); - MOZ_ASSERT(ent, "Why are you using a key we didn't claim to have?"); - return ent->mData; + return mEntries; } - DataType& Get(const nsAString& aKey) + nsTArray& Entries() { - EntryType* ent = this->GetEntry(aKey); - MOZ_ASSERT(ent, "Why are you using a key we didn't claim to have?"); - return ent->mData; + return mEntries; } - // The return value is only safe to use until an AddEntry call. - const DataType* GetIfExists(const nsAString& aKey) const - { - const EntryType* ent = this->GetEntry(aKey); - if (!ent) { - return nullptr; - } - return &ent->mData; - } - - void GetKeys(nsTArray& aKeys) const { - for (auto iter = this->ConstIter(); !iter.Done(); iter.Next()) { - aKeys.AppendElement(iter.Get()->GetKey()); - } - } - - // XXXbz we expose this generic enumerator for tracing. Otherwise we'd end up - // with a dependency on BindingUtils.h here for the SequenceTracer bits. - typedef void (* Enumerator)(DataType* aValue, void* aClosure); - void EnumerateValues(Enumerator aEnumerator, void *aClosure) - { - for (auto iter = this->Iter(); !iter.Done(); iter.Next()) { - aEnumerator(&iter.Get()->mData, aClosure); - } - } - - MOZ_MUST_USE - DataType* AddEntry(const nsAString& aKey) - { - EntryType* ent = this->PutEntry(aKey, fallible); - if (!ent) { - return nullptr; - } - return &ent->mData; - } +private: + nsTArray mEntries; }; } // namespace dom diff --git a/dom/fetch/InternalHeaders.cpp b/dom/fetch/InternalHeaders.cpp index 11585615e..83a686785 100644 --- a/dom/fetch/InternalHeaders.cpp +++ b/dom/fetch/InternalHeaders.cpp @@ -316,10 +316,11 @@ InternalHeaders::Fill(const Sequence>& aInit, ErrorResult& a void InternalHeaders::Fill(const MozMap& aInit, ErrorResult& aRv) { - nsTArray keys; - aInit.GetKeys(keys); - for (uint32_t i = 0; i < keys.Length() && !aRv.Failed(); ++i) { - Append(NS_ConvertUTF16toUTF8(keys[i]), aInit.Get(keys[i]), aRv); + for (auto& entry : aInit.Entries()) { + Append(NS_ConvertUTF16toUTF8(entry.mKey), entry.mValue, aRv); + if (aRv.Failed()) { + return; + } } } -- cgit v1.2.3 From cfcba2402e625f94cf08acd3b6410d7513ba0b2e Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 18:49:40 +0200 Subject: Fix up some minor issues with default value handling in codegen --- dom/bindings/Codegen.py | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index fd811bb3a..378ecf737 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4290,6 +4290,9 @@ class JSToNativeConversionInfo(): for whether we have a JS::Value. Only used when defaultValue is not None or when True is passed for checkForValue to instantiateJSToNativeConversion. + This expression may not be already-parenthesized, so if + you use it with && or || make sure to put parens + around it. ${passedToJSImpl} replaced by an expression that evaluates to a boolean for whether this value is being passed to a JS- implemented interface. @@ -5146,7 +5149,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, if isinstance(defaultValue, IDLNullValue): extraConditionForNull = "!(${haveValue}) || " else: - extraConditionForNull = "${haveValue} && " + extraConditionForNull = "(${haveValue}) && " else: extraConditionForNull = "" templateBody = handleNull(templateBody, declLoc, @@ -5690,7 +5693,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, haveCallable = "${val}.isObject() && " + haveCallable if defaultValue is not None: assert(isinstance(defaultValue, IDLNullValue)) - haveCallable = "${haveValue} && " + haveCallable + haveCallable = "(${haveValue}) && " + haveCallable template = ( ("if (%s) {\n" % haveCallable) + conversion + @@ -5702,7 +5705,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, haveObject = "${val}.isObject()" if defaultValue is not None: assert(isinstance(defaultValue, IDLNullValue)) - haveObject = "${haveValue} && " + haveObject + haveObject = "(${haveValue}) && " + haveObject template = CGIfElseWrapper(haveObject, CGGeneric(conversion), CGGeneric("${declName} = nullptr;\n")).define() @@ -5770,8 +5773,9 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, return handleJSObjectType(type, isMember, failureCode, exceptionCode, sourceDescription) if type.isDictionary(): - # There are no nullable dictionaries - assert not type.nullable() or isCallbackReturnValue + # There are no nullable dictionary arguments or dictionary members + assert(not type.nullable() or isCallbackReturnValue or + (isMember and isMember != "Dictionary")) # All optional dictionaries always have default values, so we # should be able to assume not isOptional here. assert not isOptional -- cgit v1.2.3 From 50059d734a07f85214dbb5cbdc2d505f274752a0 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 18:52:13 +0200 Subject: Disallow mozmap-typed constants --- dom/bindings/parser/WebIDL.py | 3 +++ 1 file changed, 3 insertions(+) diff --git a/dom/bindings/parser/WebIDL.py b/dom/bindings/parser/WebIDL.py index f668d7d62..7d06dbcec 100644 --- a/dom/bindings/parser/WebIDL.py +++ b/dom/bindings/parser/WebIDL.py @@ -3843,6 +3843,9 @@ class IDLConst(IDLInterfaceMember): if type.isDictionary(): raise WebIDLError("A constant cannot be of a dictionary type", [self.location]) + if type.isMozMap(): + raise WebIDLError("A constant cannot be of a MozMap type", + [self.location]) self.type = type self.value = value -- cgit v1.2.3 From 7d411777a35aedc5cd5f31e58e3d3468a20320b8 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 19:01:09 +0200 Subject: Add some tests for distinguishability of unions --- dom/bindings/parser/WebIDL.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/dom/bindings/parser/WebIDL.py b/dom/bindings/parser/WebIDL.py index 7d06dbcec..8c71333fa 100644 --- a/dom/bindings/parser/WebIDL.py +++ b/dom/bindings/parser/WebIDL.py @@ -2321,8 +2321,10 @@ class IDLNullableType(IDLParameterizedType): return self def isDistinguishableFrom(self, other): - if (other.nullable() or (other.isUnion() and other.hasNullableType) or - other.isDictionary()): + if (other.nullable() or + other.isDictionary() or + (other.isUnion() and + (other.hasNullableType or other.hasDictionaryType()))): # Can't tell which type null should become return False return self.inner.isDistinguishableFrom(other) -- cgit v1.2.3 From e17501d5ebc3eb019905be985a3addf3732b2fef Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 19:03:07 +0200 Subject: Change JS to MozMap conversion to more closely follow the record<> spec --- dom/bindings/Codegen.py | 30 ++++++++++++++++++++++++------ 1 file changed, 24 insertions(+), 6 deletions(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index 378ecf737..1f0f2d9bf 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4780,8 +4780,11 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, auto& mozMapEntries = ${mozMapRef}.Entries(); JS::Rooted mozMapObj(cx, &$${val}.toObject()); - JS::Rooted ids(cx, JS::IdVector(cx)); - if (!JS_Enumerate(cx, mozMapObj, &ids)) { + JS::AutoIdVector ids(cx); + // Keep skipping symbols until + // https://github.com/heycam/webidl/issues/294 is sorted out. + if (!js::GetPropertyKeys(cx, mozMapObj, + JSITER_OWNONLY | JSITER_HIDDEN, &ids)) { $*{exceptionCode} } if (!mozMapEntries.SetCapacity(ids.length(), mozilla::fallible)) { @@ -4793,14 +4796,29 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, JS::Rooted curId(cx); for (size_t i = 0; i < ids.length(); ++i) { curId = ids[i]; + + MOZ_ASSERT(!JSID_IS_SYMBOL(curId), "No symbols, we said!"); + + JS::Rooted desc(cx); + if (!JS_GetOwnPropertyDescriptorById(cx, mozMapObj, curId, + &desc)) { + $*{exceptionCode} + } + + if (!desc.object() /* == undefined in spec terms */ || + !desc.enumerable()) { + continue; + } + binding_detail::FakeString propName; bool isSymbol; - if (!ConvertIdToString(cx, curId, propName, isSymbol) || - (!isSymbol && !JS_GetPropertyById(cx, mozMapObj, curId, &temp))) { + if (!ConvertIdToString(cx, curId, propName, isSymbol)) { $*{exceptionCode} } - if (isSymbol) { - continue; + MOZ_ASSERT(!isSymbol, "We said, no symbols!"); + + if (!JS_GetPropertyById(cx, mozMapObj, curId, &temp)) { + $*{exceptionCode} } // Safe to do an infallible append here, because we did a -- cgit v1.2.3 From 3344c564a81c006633780542fa84bdbd69a51aac Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 19:05:08 +0200 Subject: Split up PrimitiveOrStringType into PrimitiveType and StringType in the Web IDL parser --- dom/bindings/parser/WebIDL.py | 60 ++++++++++++++++++++++++++----------------- 1 file changed, 36 insertions(+), 24 deletions(-) diff --git a/dom/bindings/parser/WebIDL.py b/dom/bindings/parser/WebIDL.py index 8c71333fa..22afba43e 100644 --- a/dom/bindings/parser/WebIDL.py +++ b/dom/bindings/parser/WebIDL.py @@ -6360,7 +6360,7 @@ class Parser(Tokenizer): def p_NonAnyType(self, p): """ - NonAnyType : PrimitiveOrStringType Null + NonAnyType : PrimitiveType Null | ARRAYBUFFER Null | SHAREDARRAYBUFFER Null | OBJECT Null @@ -6376,6 +6376,12 @@ class Parser(Tokenizer): p[0] = self.handleNullable(type, p[2]) + def p_NonAnyTypeStringType(self, p): + """ + NonAnyType : StringType Null + """ + p[0] = self.handleNullable(p[1], p[2]) + def p_NonAnyTypeSequenceType(self, p): """ NonAnyType : SEQUENCE LT Type GT Null @@ -6445,7 +6451,7 @@ class Parser(Tokenizer): def p_ConstType(self, p): """ - ConstType : PrimitiveOrStringType Null + ConstType : PrimitiveType Null """ type = BuiltinTypes[p[1]] p[0] = self.handleNullable(type, p[2]) @@ -6459,69 +6465,75 @@ class Parser(Tokenizer): type = IDLUnresolvedType(self.getLocation(p, 1), identifier) p[0] = self.handleNullable(type, p[2]) - def p_PrimitiveOrStringTypeUint(self, p): + def p_PrimitiveTypeUint(self, p): """ - PrimitiveOrStringType : UnsignedIntegerType + PrimitiveType : UnsignedIntegerType """ p[0] = p[1] - def p_PrimitiveOrStringTypeBoolean(self, p): + def p_PrimitiveTypeBoolean(self, p): """ - PrimitiveOrStringType : BOOLEAN + PrimitiveType : BOOLEAN """ p[0] = IDLBuiltinType.Types.boolean - def p_PrimitiveOrStringTypeByte(self, p): + def p_PrimitiveTypeByte(self, p): """ - PrimitiveOrStringType : BYTE + PrimitiveType : BYTE """ p[0] = IDLBuiltinType.Types.byte - def p_PrimitiveOrStringTypeOctet(self, p): + def p_PrimitiveTypeOctet(self, p): """ - PrimitiveOrStringType : OCTET + PrimitiveType : OCTET """ p[0] = IDLBuiltinType.Types.octet - def p_PrimitiveOrStringTypeFloat(self, p): + def p_PrimitiveTypeFloat(self, p): """ - PrimitiveOrStringType : FLOAT + PrimitiveType : FLOAT """ p[0] = IDLBuiltinType.Types.float - def p_PrimitiveOrStringTypeUnrestictedFloat(self, p): + def p_PrimitiveTypeUnrestictedFloat(self, p): """ - PrimitiveOrStringType : UNRESTRICTED FLOAT + PrimitiveType : UNRESTRICTED FLOAT """ p[0] = IDLBuiltinType.Types.unrestricted_float - def p_PrimitiveOrStringTypeDouble(self, p): + def p_PrimitiveTypeDouble(self, p): """ - PrimitiveOrStringType : DOUBLE + PrimitiveType : DOUBLE """ p[0] = IDLBuiltinType.Types.double - def p_PrimitiveOrStringTypeUnrestictedDouble(self, p): + def p_PrimitiveTypeUnrestictedDouble(self, p): """ - PrimitiveOrStringType : UNRESTRICTED DOUBLE + PrimitiveType : UNRESTRICTED DOUBLE """ p[0] = IDLBuiltinType.Types.unrestricted_double - def p_PrimitiveOrStringTypeDOMString(self, p): + def p_StringType(self, p): + """ + StringType : BuiltinStringType + """ + p[0] = BuiltinTypes[p[1]] + + def p_BuiltinStringTypeDOMString(self, p): """ - PrimitiveOrStringType : DOMSTRING + BuiltinStringType : DOMSTRING """ p[0] = IDLBuiltinType.Types.domstring - def p_PrimitiveOrStringTypeBytestring(self, p): + def p_BuiltinStringTypeBytestring(self, p): """ - PrimitiveOrStringType : BYTESTRING + BuiltinStringType : BYTESTRING """ p[0] = IDLBuiltinType.Types.bytestring - def p_PrimitiveOrStringTypeUSVString(self, p): + def p_BuiltinStringTypeUSVString(self, p): """ - PrimitiveOrStringType : USVSTRING + BuiltinStringType : USVSTRING """ p[0] = IDLBuiltinType.Types.usvstring -- cgit v1.2.3 From 5890367d30702ff8f2fbb6fc28e6ecdd6d5b2b84 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 19:37:03 +0200 Subject: Rename "MozMap" to "record" in our IDL parser and IDL files --- dom/bindings/Codegen.py | 42 +++++++++---------- dom/bindings/Configuration.py | 2 +- dom/bindings/parser/WebIDL.py | 87 +++++++++++++++++++++------------------ dom/fetch/Headers.cpp | 14 +++---- dom/fetch/Headers.h | 10 ++--- dom/webidl/Headers.webidl | 2 +- dom/webidl/InstallTrigger.webidl | 2 +- dom/webidl/TestInterfaceJS.webidl | 2 +- 8 files changed, 83 insertions(+), 78 deletions(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index 1f0f2d9bf..d7212f7bd 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -84,7 +84,7 @@ def idlTypeNeedsCycleCollection(type): return True elif type.isUnion(): return any(idlTypeNeedsCycleCollection(t) for t in type.flatMemberTypes) - elif type.isMozMap(): + elif type.isRecord(): if idlTypeNeedsCycleCollection(type.inner): raise TypeError("Cycle collection for type %s is not supported" % type) return False @@ -1171,7 +1171,7 @@ class CGHeaders(CGWrapper): declareIncludes.add(filename) elif unrolled.isPrimitive(): bindingHeaders.add("mozilla/dom/PrimitiveConversions.h") - elif unrolled.isMozMap(): + elif unrolled.isRecord(): if dictionary or jsImplementedDescriptors: declareIncludes.add("mozilla/dom/MozMap.h") else: @@ -1388,7 +1388,7 @@ def UnionTypes(unionTypes, config): # the right header to be able to Release() in our inlined # code. headers.add(CGHeaders.getDeclarationFilename(f.callback)) - elif f.isMozMap(): + elif f.isRecord(): headers.add("mozilla/dom/MozMap.h") # And add headers for the type we're parametrized over addHeadersForType(f.inner) @@ -1448,7 +1448,7 @@ def UnionConversions(unionTypes, config): headers.add(CGHeaders.getDeclarationFilename(f.inner)) elif f.isPrimitive(): headers.add("mozilla/dom/PrimitiveConversions.h") - elif f.isMozMap(): + elif f.isRecord(): headers.add("mozilla/dom/MozMap.h") # And the internal type of the MozMap addHeadersForType(f.inner) @@ -4730,7 +4730,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, dealWithOptional=isOptional, holderArgs=holderArgs) - if type.isMozMap(): + if type.isRecord(): assert not isEnforceRange and not isClamp if failureCode is None: notMozMap = ('ThrowErrorMessage(cx, MSG_NOT_OBJECT, "%s");\n' @@ -4937,7 +4937,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, else: setDictionary = None - mozMapMemberTypes = filter(lambda t: t.isMozMap(), memberTypes) + mozMapMemberTypes = filter(lambda t: t.isRecord(), memberTypes) if len(mozMapMemberTypes) > 0: assert len(mozMapMemberTypes) == 1 name = getUnionMemberName(mozMapMemberTypes[0]) @@ -6385,7 +6385,7 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, if type is None or type.isVoid(): return (setUndefined(), True) - if (type.isSequence() or type.isMozMap()) and type.nullable(): + if (type.isSequence() or type.isRecord()) and type.nullable(): # These are both wrapped in Nullable<> recTemplate, recInfall = getWrapTemplateForType(type.inner, descriptorProvider, "%s.Value()" % result, successCode, @@ -6458,7 +6458,7 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, return (code, False) - if type.isMozMap(): + if type.isRecord(): # Now do non-nullable MozMap. Our success code is just to break to # where we define the property on the object. Note that we bump the # mozMapWrapLevel around this call so that nested MozMap conversions @@ -6793,7 +6793,7 @@ def typeMatchesLambda(type, func): return False if type.nullable(): return typeMatchesLambda(type.inner, func) - if type.isSequence() or type.isMozMap(): + if type.isSequence() or type.isRecord(): return typeMatchesLambda(type.inner, func) if type.isUnion(): return any(typeMatchesLambda(t, func) for t in @@ -6889,7 +6889,7 @@ def getRetvalDeclarationForType(returnType, descriptorProvider, if nullable: result = CGTemplatedType("Nullable", result) return result, "ref", rooter, None, None - if returnType.isMozMap(): + if returnType.isRecord(): nullable = returnType.nullable() if nullable: returnType = returnType.inner @@ -6999,7 +6999,7 @@ class CGCallGenerator(CGThing): return True if a.type.isSequence(): return True - if a.type.isMozMap(): + if a.type.isRecord(): return True # isObject() types are always a JS::Rooted, whether # nullable or not, and it turns out a const JS::Rooted @@ -7222,7 +7222,7 @@ def wrapTypeIntoCurrentCompartment(type, value, isMember=True): wrapCode = CGIfWrapper(wrapCode, "!%s.IsNull()" % origValue) return wrapCode - if type.isMozMap(): + if type.isRecord(): origType = type if type.nullable(): type = type.inner @@ -8135,7 +8135,7 @@ class CGMethodCall(CGThing): genericObjectSigs = [ s for s in possibleSignatures if (distinguishingType(s).isDictionary() or - distinguishingType(s).isMozMap() or + distinguishingType(s).isRecord() or distinguishingType(s).isCallbackInterface())] assert len(genericObjectSigs) <= 1 objectSigs.extend(genericObjectSigs) @@ -9429,7 +9429,7 @@ class CGMemberJITInfo(CGThing): return "JSVAL_TYPE_UNDEFINED" if t.isSequence(): return "JSVAL_TYPE_OBJECT" - if t.isMozMap(): + if t.isRecord(): return "JSVAL_TYPE_OBJECT" if t.isGeckoInterface(): return "JSVAL_TYPE_OBJECT" @@ -9690,7 +9690,7 @@ def getUnionAccessorSignatureType(type, descriptorProvider): # Flat member types have already unwrapped nullables. assert not type.nullable() - if type.isSequence() or type.isMozMap(): + if type.isSequence() or type.isRecord(): if type.isSequence(): wrapperType = "Sequence" else: @@ -10061,7 +10061,7 @@ class CGUnionStruct(CGThing): CGCase("e" + vars["name"], CGGeneric("DoTraceSequence(trc, mValue.m%s.Value());\n" % vars["name"]))) - elif t.isMozMap(): + elif t.isRecord(): traceCases.append( CGCase("e" + vars["name"], CGGeneric("TraceMozMap(trc, mValue.m%s.Value());\n" % @@ -13193,7 +13193,7 @@ class CGDictionary(CGThing): trace = CGGeneric('%s.TraceSelf(trc);\n' % memberData) if type.nullable(): trace = CGIfWrapper(trace, "!%s.IsNull()" % memberNullable) - elif type.isMozMap(): + elif type.isRecord(): # If you implement this, add a MozMap to # TestInterfaceJSDictionary and test it in test_bug1036214.html # to make sure we end up with the correct security properties. @@ -13604,7 +13604,7 @@ class ForwardDeclarationBuilder: # since we don't know which one we might want self.addInMozillaDom(CGUnionStruct.unionTypeName(t, False)) self.addInMozillaDom(CGUnionStruct.unionTypeName(t, True)) - elif t.isMozMap(): + elif t.isRecord(): self.forwardDeclareForType(t.inner, config) # Don't need to do anything for void, primitive, string, any or object. # There may be some other cases we are missing. @@ -14110,7 +14110,7 @@ class CGNativeMember(ClassMethod): else: returnCode = "aRetVal.SwapElements(${declName});\n" return "void", "", returnCode - if type.isMozMap(): + if type.isRecord(): # If we want to handle MozMap-of-MozMap return values, we're # going to need to fix example codegen to not produce MozMap # for the relevant argument... @@ -14160,7 +14160,7 @@ class CGNativeMember(ClassMethod): if nullable: type = CGTemplatedType("Nullable", type) args.append(Argument("%s&" % type.define(), "aRetVal")) - elif returnType.isMozMap(): + elif returnType.isRecord(): nullable = returnType.nullable() if nullable: returnType = returnType.inner @@ -14238,7 +14238,7 @@ class CGNativeMember(ClassMethod): decl = CGTemplatedType("Sequence", argType) return decl.define(), True, True - if type.isMozMap(): + if type.isRecord(): nullable = type.nullable() if nullable: type = type.inner diff --git a/dom/bindings/Configuration.py b/dom/bindings/Configuration.py index 5c96580a1..f80c19c33 100644 --- a/dom/bindings/Configuration.py +++ b/dom/bindings/Configuration.py @@ -115,7 +115,7 @@ class Configuration(DescriptorProvider): for (t, _) in getAllTypes(self.descriptors, self.dictionaries, self.callbacks): while True: - if t.isMozMap(): + if t.isRecord(): t = t.inner elif t.unroll() != t: t = t.unroll() diff --git a/dom/bindings/parser/WebIDL.py b/dom/bindings/parser/WebIDL.py index 22afba43e..8c32a8738 100644 --- a/dom/bindings/parser/WebIDL.py +++ b/dom/bindings/parser/WebIDL.py @@ -1867,7 +1867,7 @@ class IDLDictionary(IDLObjectWithScope): if (memberType.nullable() or memberType.isSequence() or - memberType.isMozMap()): + memberType.isRecord()): return typeContainsDictionary(memberType.inner, dictionary) if memberType.isDictionary(): @@ -1988,7 +1988,7 @@ class IDLType(IDLObject): 'callback', 'union', 'sequence', - 'mozmap' + 'record' ) def __init__(self, location, name): @@ -2038,7 +2038,7 @@ class IDLType(IDLObject): def isSequence(self): return False - def isMozMap(self): + def isRecord(self): return False def isArrayBuffer(self): @@ -2263,8 +2263,8 @@ class IDLNullableType(IDLParameterizedType): def isSequence(self): return self.inner.isSequence() - def isMozMap(self): - return self.inner.isMozMap() + def isRecord(self): + return self.inner.isRecord() def isArrayBuffer(self): return self.inner.isArrayBuffer() @@ -2399,34 +2399,38 @@ class IDLSequenceType(IDLParameterizedType): return (other.isPrimitive() or other.isString() or other.isEnum() or other.isDate() or other.isInterface() or other.isDictionary() or - other.isCallback() or other.isMozMap()) + other.isCallback() or other.isRecord()) -class IDLMozMapType(IDLParameterizedType): - def __init__(self, location, parameterType): - assert not parameterType.isVoid() +class IDLRecordType(IDLParameterizedType): + def __init__(self, location, keyType, valueType): + assert keyType.isString() + assert keyType.isComplete() + assert not valueType.isVoid() + + IDLParameterizedType.__init__(self, location, valueType.name, valueType) + self.keyType = keyType - IDLParameterizedType.__init__(self, location, parameterType.name, parameterType) # Need to set self.name up front if our inner type is already complete, # since in that case our .complete() won't be called. if self.inner.isComplete(): - self.name = self.inner.name + "MozMap" + self.name = self.keyType.name + self.inner.name + "Record" def __eq__(self, other): - return isinstance(other, IDLMozMapType) and self.inner == other.inner + return isinstance(other, IDLRecordType) and self.inner == other.inner def __str__(self): - return self.inner.__str__() + "MozMap" + return self.keyType.__str__() + self.inner.__str__() + "Record" - def isMozMap(self): + def isRecord(self): return True def tag(self): - return IDLType.Tags.mozmap + return IDLType.Tags.record def complete(self, scope): self.inner = self.inner.complete(scope) - self.name = self.inner.name + "MozMap" + self.name = self.keyType.name + self.inner.name + "Record" return self def unroll(self): @@ -2616,8 +2620,8 @@ class IDLTypedefType(IDLType): def isSequence(self): return self.inner.isSequence() - def isMozMap(self): - return self.inner.isMozMap() + def isRecord(self): + return self.inner.isRecord() def isDictionary(self): return self.inner.isDictionary() @@ -2800,7 +2804,7 @@ class IDLWrapperType(IDLType): if self.isEnum(): return (other.isPrimitive() or other.isInterface() or other.isObject() or other.isCallback() or other.isDictionary() or - other.isSequence() or other.isMozMap() or other.isDate()) + other.isSequence() or other.isRecord() or other.isDate()) if self.isDictionary() and other.nullable(): return False if (other.isPrimitive() or other.isString() or other.isEnum() or @@ -2822,7 +2826,7 @@ class IDLWrapperType(IDLType): (self.isNonCallbackInterface() or other.isNonCallbackInterface())) if (other.isDictionary() or other.isCallback() or - other.isMozMap()): + other.isRecord()): return self.isNonCallbackInterface() # Not much else |other| can be @@ -3032,17 +3036,17 @@ class IDLBuiltinType(IDLType): return (other.isNumeric() or other.isString() or other.isEnum() or other.isInterface() or other.isObject() or other.isCallback() or other.isDictionary() or - other.isSequence() or other.isMozMap() or other.isDate()) + other.isSequence() or other.isRecord() or other.isDate()) if self.isNumeric(): return (other.isBoolean() or other.isString() or other.isEnum() or other.isInterface() or other.isObject() or other.isCallback() or other.isDictionary() or - other.isSequence() or other.isMozMap() or other.isDate()) + other.isSequence() or other.isRecord() or other.isDate()) if self.isString(): return (other.isPrimitive() or other.isInterface() or other.isObject() or other.isCallback() or other.isDictionary() or - other.isSequence() or other.isMozMap() or other.isDate()) + other.isSequence() or other.isRecord() or other.isDate()) if self.isAny(): # Can't tell "any" apart from anything return False @@ -3052,7 +3056,7 @@ class IDLBuiltinType(IDLType): return (other.isPrimitive() or other.isString() or other.isEnum() or other.isInterface() or other.isCallback() or other.isDictionary() or other.isSequence() or - other.isMozMap()) + other.isRecord()) if self.isVoid(): return not other.isVoid() # Not much else we could be! @@ -3060,7 +3064,7 @@ class IDLBuiltinType(IDLType): # Like interfaces, but we know we're not a callback return (other.isPrimitive() or other.isString() or other.isEnum() or other.isCallback() or other.isDictionary() or - other.isSequence() or other.isMozMap() or other.isDate() or + other.isSequence() or other.isRecord() or other.isDate() or (other.isInterface() and ( # ArrayBuffer is distinguishable from everything # that's not an ArrayBuffer or a callback interface @@ -3845,8 +3849,8 @@ class IDLConst(IDLInterfaceMember): if type.isDictionary(): raise WebIDLError("A constant cannot be of a dictionary type", [self.location]) - if type.isMozMap(): - raise WebIDLError("A constant cannot be of a MozMap type", + if type.isRecord(): + raise WebIDLError("A constant cannot be of a record type", [self.location]) self.type = type self.value = value @@ -3959,8 +3963,8 @@ class IDLAttribute(IDLInterfaceMember): if self.type.isSequence() and not self.getExtendedAttribute("Cached"): raise WebIDLError("A non-cached attribute cannot be of a sequence " "type", [self.location]) - if self.type.isMozMap() and not self.getExtendedAttribute("Cached"): - raise WebIDLError("A non-cached attribute cannot be of a MozMap " + if self.type.isRecord() and not self.getExtendedAttribute("Cached"): + raise WebIDLError("A non-cached attribute cannot be of a record " "type", [self.location]) if self.type.isUnion(): for f in self.type.unroll().flatMemberTypes: @@ -3976,11 +3980,11 @@ class IDLAttribute(IDLInterfaceMember): "one of its member types's member " "types, and so on) is a sequence " "type", [self.location, f.location]) - if f.isMozMap(): + if f.isRecord(): raise WebIDLError("An attribute cannot be of a union " "type if one of its member types (or " "one of its member types's member " - "types, and so on) is a MozMap " + "types, and so on) is a record " "type", [self.location, f.location]) if not self.type.isInterface() and self.getExtendedAttribute("PutForwards"): raise WebIDLError("An attribute with [PutForwards] must have an " @@ -3994,7 +3998,7 @@ class IDLAttribute(IDLInterfaceMember): def typeContainsChromeOnlyDictionaryMember(type): if (type.nullable() or type.isSequence() or - type.isMozMap()): + type.isRecord()): return typeContainsChromeOnlyDictionaryMember(type.inner) if type.isUnion(): @@ -4040,10 +4044,10 @@ class IDLAttribute(IDLInterfaceMember): [self.location, location]) if self.getExtendedAttribute("Frozen"): if (not self.type.isSequence() and not self.type.isDictionary() and - not self.type.isMozMap()): + not self.type.isRecord()): raise WebIDLError("[Frozen] is only allowed on " "sequence-valued, dictionary-valued, and " - "MozMap-valued attributes", + "record-valued attributes", [self.location]) if not self.type.unroll().isExposedInAllOf(self.exposureSet): raise WebIDLError("Attribute returns a type that is not exposed " @@ -5152,7 +5156,7 @@ class Tokenizer(object): "Promise": "PROMISE", "required": "REQUIRED", "sequence": "SEQUENCE", - "MozMap": "MOZMAP", + "record": "RECORD", "short": "SHORT", "unsigned": "UNSIGNED", "void": "VOID", @@ -6281,7 +6285,7 @@ class Parser(Tokenizer): | OCTET | OPTIONAL | SEQUENCE - | MOZMAP + | RECORD | SETTER | SHORT | STATIC @@ -6402,13 +6406,14 @@ class Parser(Tokenizer): type = IDLUnresolvedType(self.getLocation(p, 1), promiseIdent, p[3]) p[0] = self.handleNullable(type, p[5]) - def p_NonAnyTypeMozMapType(self, p): + def p_NonAnyTypeRecordType(self, p): """ - NonAnyType : MOZMAP LT Type GT Null + NonAnyType : RECORD LT StringType COMMA Type GT Null """ - innerType = p[3] - type = IDLMozMapType(self.getLocation(p, 1), innerType) - p[0] = self.handleNullable(type, p[5]) + keyType = p[3] + valueType = p[5] + type = IDLRecordType(self.getLocation(p, 1), keyType, valueType) + p[0] = self.handleNullable(type, p[7]) def p_NonAnyTypeScopedName(self, p): """ diff --git a/dom/fetch/Headers.cpp b/dom/fetch/Headers.cpp index 1e1a46c62..ca5aa57a6 100644 --- a/dom/fetch/Headers.cpp +++ b/dom/fetch/Headers.cpp @@ -25,7 +25,7 @@ NS_INTERFACE_MAP_END // static already_AddRefed Headers::Constructor(const GlobalObject& aGlobal, - const Optional& aInit, + const Optional& aInit, ErrorResult& aRv) { RefPtr ih = new InternalHeaders(); @@ -39,8 +39,8 @@ Headers::Constructor(const GlobalObject& aGlobal, ih->Fill(*aInit.Value().GetAsHeaders().mInternalHeaders, aRv); } else if (aInit.Value().IsByteStringSequenceSequence()) { ih->Fill(aInit.Value().GetAsByteStringSequenceSequence(), aRv); - } else if (aInit.Value().IsByteStringMozMap()) { - ih->Fill(aInit.Value().GetAsByteStringMozMap(), aRv); + } else if (aInit.Value().IsByteStringByteStringRecord()) { + ih->Fill(aInit.Value().GetAsByteStringByteStringRecord(), aRv); } if (aRv.Failed()) { @@ -53,7 +53,7 @@ Headers::Constructor(const GlobalObject& aGlobal, // static already_AddRefed Headers::Constructor(const GlobalObject& aGlobal, - const OwningHeadersOrByteStringSequenceSequenceOrByteStringMozMap& aInit, + const OwningHeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord& aInit, ErrorResult& aRv) { nsCOMPtr global = do_QueryInterface(aGlobal.GetAsSupports()); @@ -62,7 +62,7 @@ Headers::Constructor(const GlobalObject& aGlobal, /* static */ already_AddRefed Headers::Create(nsIGlobalObject* aGlobal, - const OwningHeadersOrByteStringSequenceSequenceOrByteStringMozMap& aInit, + const OwningHeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord& aInit, ErrorResult& aRv) { RefPtr ih = new InternalHeaders(); @@ -72,8 +72,8 @@ Headers::Create(nsIGlobalObject* aGlobal, ih->Fill(*(aInit.GetAsHeaders().get()->mInternalHeaders), aRv); } else if (aInit.IsByteStringSequenceSequence()) { ih->Fill(aInit.GetAsByteStringSequenceSequence(), aRv); - } else if (aInit.IsByteStringMozMap()) { - ih->Fill(aInit.GetAsByteStringMozMap(), aRv); + } else if (aInit.IsByteStringByteStringRecord()) { + ih->Fill(aInit.GetAsByteStringByteStringRecord(), aRv); } if (NS_WARN_IF(aRv.Failed())) { diff --git a/dom/fetch/Headers.h b/dom/fetch/Headers.h index b603dc836..38b0fc68f 100644 --- a/dom/fetch/Headers.h +++ b/dom/fetch/Headers.h @@ -21,8 +21,8 @@ class ErrorResult; namespace dom { template class MozMap; -class HeadersOrByteStringSequenceSequenceOrByteStringMozMap; -class OwningHeadersOrByteStringSequenceSequenceOrByteStringMozMap; +class HeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord; +class OwningHeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord; /** * This Headers class is only used to represent the content facing Headers @@ -57,17 +57,17 @@ public: static already_AddRefed Constructor(const GlobalObject& aGlobal, - const Optional& aInit, + const Optional& aInit, ErrorResult& aRv); static already_AddRefed Constructor(const GlobalObject& aGlobal, - const OwningHeadersOrByteStringSequenceSequenceOrByteStringMozMap& aInit, + const OwningHeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord& aInit, ErrorResult& aRv); static already_AddRefed Create(nsIGlobalObject* aGlobalObject, - const OwningHeadersOrByteStringSequenceSequenceOrByteStringMozMap& aInit, + const OwningHeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord& aInit, ErrorResult& aRv); void Append(const nsACString& aName, const nsACString& aValue, diff --git a/dom/webidl/Headers.webidl b/dom/webidl/Headers.webidl index 205ab9f9e..eef552a7f 100644 --- a/dom/webidl/Headers.webidl +++ b/dom/webidl/Headers.webidl @@ -8,7 +8,7 @@ * http://fetch.spec.whatwg.org/#headers-class */ -typedef (Headers or sequence> or MozMap) HeadersInit; +typedef (Headers or sequence> or record) HeadersInit; enum HeadersGuardEnum { "none", diff --git a/dom/webidl/InstallTrigger.webidl b/dom/webidl/InstallTrigger.webidl index 789fb2bc4..68f48ddc6 100644 --- a/dom/webidl/InstallTrigger.webidl +++ b/dom/webidl/InstallTrigger.webidl @@ -57,7 +57,7 @@ interface InstallTriggerImpl { * A callback to call as each installation succeeds or fails * @return true if the installations were successfully started */ - boolean install(MozMap<(DOMString or InstallTriggerData)> installs, + boolean install(record installs, optional InstallTriggerCallback callback); /** diff --git a/dom/webidl/TestInterfaceJS.webidl b/dom/webidl/TestInterfaceJS.webidl index 1ca629c39..2cf8d701a 100644 --- a/dom/webidl/TestInterfaceJS.webidl +++ b/dom/webidl/TestInterfaceJS.webidl @@ -24,7 +24,7 @@ interface TestInterfaceJS : EventTarget { any pingPongObjectOrString((object or DOMString) objOrString); TestInterfaceJSDictionary pingPongDictionary(optional TestInterfaceJSDictionary dict); long pingPongDictionaryOrLong(optional (TestInterfaceJSUnionableDictionary or long) dictOrLong); - DOMString pingPongMap(MozMap map); + DOMString pingPongMap(record map); long objectSequenceLength(sequence seq); long anySequenceLength(sequence seq); -- cgit v1.2.3 From b586a191ec085d2c6c5c4fdfb1b12102fb5de4c4 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 20:04:13 +0200 Subject: Rename the MozMap C++ type to "record" and give it a template parameter for the key type --- dom/bindings/BindingUtils.h | 61 +++++++-------- dom/bindings/Codegen.py | 169 +++++++++++++++++++++++------------------- dom/bindings/MozMap.h | 31 ++++---- dom/bindings/moz.build | 2 +- dom/fetch/Headers.h | 2 +- dom/fetch/InternalHeaders.cpp | 2 +- dom/fetch/InternalHeaders.h | 4 +- 7 files changed, 145 insertions(+), 126 deletions(-) diff --git a/dom/bindings/BindingUtils.h b/dom/bindings/BindingUtils.h index 23bbbea5a..e017b986a 100644 --- a/dom/bindings/BindingUtils.h +++ b/dom/bindings/BindingUtils.h @@ -49,7 +49,7 @@ namespace mozilla { enum UseCounter : int16_t; namespace dom { -template class MozMap; +template class Record; nsresult UnwrapArgImpl(JS::Handle src, const nsIID& iid, void** ppArg); @@ -2293,25 +2293,26 @@ public: } }; -template -void TraceMozMap(JSTracer* trc, MozMap& map) +template +void TraceRecord(JSTracer* trc, Record& record) { - for (auto& entry : map.Entries()) { + for (auto& entry : record.Entries()) { // Act like it's a one-element sequence to leverage all that infrastructure. - SequenceTracer::TraceSequence(trc, &entry.mValue, &entry.mValue + 1); + SequenceTracer::TraceSequence(trc, &entry.mValue, &entry.mValue + 1); } } -// sequence -template -class SequenceTracer, false, false, false> +// sequence +template +class SequenceTracer, false, false, false> { explicit SequenceTracer() = delete; // Should never be instantiated public: - static void TraceSequence(JSTracer* trc, MozMap* seqp, MozMap* end) { + static void TraceSequence(JSTracer* trc, Record* seqp, + Record* end) { for (; seqp != end; ++seqp) { - TraceMozMap(trc, *seqp); + TraceRecord(trc, *seqp); } } }; @@ -2389,51 +2390,51 @@ public: SequenceType mSequenceType; }; -// Rooter class for MozMap; this is what we mostly use in the codegen. -template -class MOZ_RAII MozMapRooter final : private JS::CustomAutoRooter +// Rooter class for Record; this is what we mostly use in the codegen. +template +class MOZ_RAII RecordRooter final : private JS::CustomAutoRooter { public: - MozMapRooter(JSContext *aCx, MozMap* aMozMap + RecordRooter(JSContext *aCx, Record* aRecord MOZ_GUARD_OBJECT_NOTIFIER_PARAM) : JS::CustomAutoRooter(aCx MOZ_GUARD_OBJECT_NOTIFIER_PARAM_TO_PARENT), - mMozMap(aMozMap), - mMozMapType(eMozMap) + mRecord(aRecord), + mRecordType(eRecord) { } - MozMapRooter(JSContext *aCx, Nullable>* aMozMap + RecordRooter(JSContext *aCx, Nullable>* aRecord MOZ_GUARD_OBJECT_NOTIFIER_PARAM) : JS::CustomAutoRooter(aCx MOZ_GUARD_OBJECT_NOTIFIER_PARAM_TO_PARENT), - mNullableMozMap(aMozMap), - mMozMapType(eNullableMozMap) + mNullableRecord(aRecord), + mRecordType(eNullableRecord) { } private: - enum MozMapType { - eMozMap, - eNullableMozMap + enum RecordType { + eRecord, + eNullableRecord }; virtual void trace(JSTracer *trc) override { - if (mMozMapType == eMozMap) { - TraceMozMap(trc, *mMozMap); + if (mRecordType == eRecord) { + TraceRecord(trc, *mRecord); } else { - MOZ_ASSERT(mMozMapType == eNullableMozMap); - if (!mNullableMozMap->IsNull()) { - TraceMozMap(trc, mNullableMozMap->Value()); + MOZ_ASSERT(mRecordType == eNullableRecord); + if (!mNullableRecord->IsNull()) { + TraceRecord(trc, mNullableRecord->Value()); } } } union { - MozMap* mMozMap; - Nullable>* mNullableMozMap; + Record* mRecord; + Nullable>* mNullableRecord; }; - MozMapType mMozMapType; + RecordType mRecordType; }; template diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index d7212f7bd..ff6fa0ea3 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -996,6 +996,8 @@ class CGElseChain(CGThing): class CGTemplatedType(CGWrapper): def __init__(self, templateName, child, isConst=False, isReference=False): + if isinstance(child, list): + child = CGList(child, ", ") const = "const " if isConst else "" pre = "%s%s<" % (const, templateName) ref = "&" if isReference else "" @@ -1173,10 +1175,10 @@ class CGHeaders(CGWrapper): bindingHeaders.add("mozilla/dom/PrimitiveConversions.h") elif unrolled.isRecord(): if dictionary or jsImplementedDescriptors: - declareIncludes.add("mozilla/dom/MozMap.h") + declareIncludes.add("mozilla/dom/Record.h") else: - bindingHeaders.add("mozilla/dom/MozMap.h") - # Also add headers for the type the MozMap is + bindingHeaders.add("mozilla/dom/Record.h") + # Also add headers for the type the record is # parametrized over, if needed. addHeadersForType((t.inner, dictionary)) @@ -1389,7 +1391,7 @@ def UnionTypes(unionTypes, config): # code. headers.add(CGHeaders.getDeclarationFilename(f.callback)) elif f.isRecord(): - headers.add("mozilla/dom/MozMap.h") + headers.add("mozilla/dom/Record.h") # And add headers for the type we're parametrized over addHeadersForType(f.inner) @@ -1449,8 +1451,8 @@ def UnionConversions(unionTypes, config): elif f.isPrimitive(): headers.add("mozilla/dom/PrimitiveConversions.h") elif f.isRecord(): - headers.add("mozilla/dom/MozMap.h") - # And the internal type of the MozMap + headers.add("mozilla/dom/Record.h") + # And the internal type of the record addHeadersForType(f.inner) # We plan to include UnionTypes.h no matter what, so it's @@ -4370,6 +4372,13 @@ def handleDefaultStringValue(defaultValue, method): } +def recordKeyDeclType(recordType): + assert recordType.keyType.isString() + if recordType.keyType.isByteString(): + return CGGeneric("nsCString") + return CGGeneric("nsString") + + # If this function is modified, modify CGNativeMember.getArg and # CGNativeMember.getRetvalInfo accordingly. The latter cares about the decltype # and holdertype we end up using, because it needs to be able to return the code @@ -4564,7 +4573,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, declArgs = "cx" else: assert (isMember in - ("Sequence", "Variadic", "Dictionary", "OwningUnion", "MozMap")) + ("Sequence", "Variadic", "Dictionary", "OwningUnion", "Record")) # We'll get traced by the sequence or dictionary or union tracer declType = CGGeneric("JSObject*") declArgs = None @@ -4733,36 +4742,38 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, if type.isRecord(): assert not isEnforceRange and not isClamp if failureCode is None: - notMozMap = ('ThrowErrorMessage(cx, MSG_NOT_OBJECT, "%s");\n' + notRecord = ('ThrowErrorMessage(cx, MSG_NOT_OBJECT, "%s");\n' "%s" % (firstCap(sourceDescription), exceptionCode)) else: - notMozMap = failureCode + notRecord = failureCode nullable = type.nullable() # Be very careful not to change "type": we need it later if nullable: - valueType = type.inner.inner + recordType = type.inner else: - valueType = type.inner + recordType = type + valueType = recordType.inner valueInfo = getJSToNativeConversionInfo( - valueType, descriptorProvider, isMember="MozMap", + valueType, descriptorProvider, isMember="Record", exceptionCode=exceptionCode, lenientFloatCode=lenientFloatCode, isCallbackReturnValue=isCallbackReturnValue, sourceDescription="value in %s" % sourceDescription, nestingLevel=incrementNestingLevel()) if valueInfo.dealWithOptional: - raise TypeError("Shouldn't have optional things in MozMap") + raise TypeError("Shouldn't have optional things in record") if valueInfo.holderType is not None: - raise TypeError("Shouldn't need holders for MozMap") + raise TypeError("Shouldn't need holders for record") - typeName = CGTemplatedType("MozMap", valueInfo.declType) - mozMapType = typeName.define() + declType = CGTemplatedType("Record", [recordKeyDeclType(recordType), + valueInfo.declType]) + typeName = declType.define() if nullable: - typeName = CGTemplatedType("Nullable", typeName) - mozMapRef = "${declName}.SetValue()" + declType = CGTemplatedType("Nullable", declType) + recordRef = "${declName}.SetValue()" else: - mozMapRef = "${declName}" + recordRef = "${declName}" valueConversion = string.Template(valueInfo.template).substitute({ "val": "temp", @@ -4777,17 +4788,17 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, templateBody = fill( """ - auto& mozMapEntries = ${mozMapRef}.Entries(); + auto& recordEntries = ${recordRef}.Entries(); - JS::Rooted mozMapObj(cx, &$${val}.toObject()); + JS::Rooted recordObj(cx, &$${val}.toObject()); JS::AutoIdVector ids(cx); // Keep skipping symbols until // https://github.com/heycam/webidl/issues/294 is sorted out. - if (!js::GetPropertyKeys(cx, mozMapObj, + if (!js::GetPropertyKeys(cx, recordObj, JSITER_OWNONLY | JSITER_HIDDEN, &ids)) { $*{exceptionCode} } - if (!mozMapEntries.SetCapacity(ids.length(), mozilla::fallible)) { + if (!recordEntries.SetCapacity(ids.length(), mozilla::fallible)) { JS_ReportOutOfMemory(cx); $*{exceptionCode} } @@ -4800,7 +4811,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, MOZ_ASSERT(!JSID_IS_SYMBOL(curId), "No symbols, we said!"); JS::Rooted desc(cx); - if (!JS_GetOwnPropertyDescriptorById(cx, mozMapObj, curId, + if (!JS_GetOwnPropertyDescriptorById(cx, recordObj, curId, &desc)) { $*{exceptionCode} } @@ -4817,44 +4828,45 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, } MOZ_ASSERT(!isSymbol, "We said, no symbols!"); - if (!JS_GetPropertyById(cx, mozMapObj, curId, &temp)) { + if (!JS_GetPropertyById(cx, recordObj, curId, &temp)) { $*{exceptionCode} } // Safe to do an infallible append here, because we did a // SetCapacity above to the right capacity. - ${mozMapType}::EntryType* entry = mozMapEntries.AppendElement(); + ${typeName}::EntryType* entry = recordEntries.AppendElement(); entry->mKey = propName; ${valueType}& slot = entry->mValue; $*{valueConversion} } """, exceptionCode=exceptionCode, - mozMapRef=mozMapRef, - mozMapType=mozMapType, + recordRef=recordRef, + typeName=typeName, valueType=valueInfo.declType.define(), valueConversion=valueConversion) templateBody = wrapObjectTemplate(templateBody, type, "${declName}.SetNull();\n", - notMozMap) + notRecord) - declType = typeName declArgs = None holderType = None holderArgs = None - # MozMap arguments that might contain traceable things need + # record arguments that might contain traceable things need # to get traced if not isMember and isCallbackReturnValue: # Go ahead and just convert directly into our actual return value declType = CGWrapper(declType, post="&") declArgs = "aRetVal" elif not isMember and typeNeedsRooting(valueType): - holderType = CGTemplatedType("MozMapRooter", valueInfo.declType) - # If our MozMap is nullable, this will set the Nullable to be + holderType = CGTemplatedType("RecordRooter", + [recordKeyDeclType(recordType), + valueInfo.declType]) + # If our record is nullable, this will set the Nullable to be # not-null, but that's ok because we make an explicit SetNull() call # on it as needed if our JS value is actually null. - holderArgs = "cx, &%s" % mozMapRef + holderArgs = "cx, &%s" % recordRef return JSToNativeConversionInfo(templateBody, declType=declType, declArgs=declArgs, @@ -4937,16 +4949,16 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, else: setDictionary = None - mozMapMemberTypes = filter(lambda t: t.isRecord(), memberTypes) - if len(mozMapMemberTypes) > 0: - assert len(mozMapMemberTypes) == 1 - name = getUnionMemberName(mozMapMemberTypes[0]) - mozMapObject = CGGeneric( + recordMemberTypes = filter(lambda t: t.isRecord(), memberTypes) + if len(recordMemberTypes) > 0: + assert len(recordMemberTypes) == 1 + name = getUnionMemberName(recordMemberTypes[0]) + recordObject = CGGeneric( "done = (failed = !%s.TrySetTo%s(cx, ${val}, tryNext, ${passedToJSImpl})) || !tryNext;\n" % (unionArgumentObj, name)) names.append(name) else: - mozMapObject = None + recordObject = None objectMemberTypes = filter(lambda t: t.isObject(), memberTypes) if len(objectMemberTypes) > 0: @@ -4962,10 +4974,10 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, else: object = None - hasObjectTypes = interfaceObject or sequenceObject or dateObject or callbackObject or object or mozMapObject + hasObjectTypes = interfaceObject or sequenceObject or dateObject or callbackObject or object or recordObject if hasObjectTypes: # "object" is not distinguishable from other types - assert not object or not (interfaceObject or sequenceObject or dateObject or callbackObject or mozMapObject) + assert not object or not (interfaceObject or sequenceObject or dateObject or callbackObject or recordObject) if sequenceObject or dateObject or callbackObject: # An object can be both an sequence object and a callback or # dictionary, but we shouldn't have both in the union's members @@ -4985,9 +4997,9 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, if dateObject: templateBody.prepend(CGGeneric("JS::Rooted argObj(cx, &${val}.toObject());\n")) - if mozMapObject: + if recordObject: templateBody = CGList([templateBody, - CGIfWrapper(mozMapObject, "!done")]) + CGIfWrapper(recordObject, "!done")]) templateBody = CGIfWrapper(templateBody, "${val}.isObject()") else: @@ -5747,7 +5759,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, assert not isEnforceRange and not isClamp declArgs = None - if isMember in ("Variadic", "Sequence", "Dictionary", "MozMap"): + if isMember in ("Variadic", "Sequence", "Dictionary", "Record"): # Rooting is handled by the sequence and dictionary tracers. declType = "JS::Value" else: @@ -6280,7 +6292,7 @@ def getMaybeWrapValueFuncForType(type): sequenceWrapLevel = 0 -mozMapWrapLevel = 0 +recordWrapLevel = 0 def getWrapTemplateForType(type, descriptorProvider, result, successCode, @@ -6459,13 +6471,13 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, return (code, False) if type.isRecord(): - # Now do non-nullable MozMap. Our success code is just to break to + # Now do non-nullable record. Our success code is just to break to # where we define the property on the object. Note that we bump the - # mozMapWrapLevel around this call so that nested MozMap conversions + # recordWrapLevel around this call so that nested record conversions # will use different temp value names. - global mozMapWrapLevel - valueName = "mozMapValue%d" % mozMapWrapLevel - mozMapWrapLevel += 1 + global recordWrapLevel + valueName = "recordValue%d" % recordWrapLevel + recordWrapLevel += 1 innerTemplate = wrapForType( type.inner, descriptorProvider, { @@ -6478,7 +6490,7 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, 'obj': "returnObj", 'typedArraysAreStructs': typedArraysAreStructs }) - mozMapWrapLevel -= 1 + recordWrapLevel -= 1 code = fill( """ @@ -6895,14 +6907,15 @@ def getRetvalDeclarationForType(returnType, descriptorProvider, returnType = returnType.inner result, _, _, _, _ = getRetvalDeclarationForType(returnType.inner, descriptorProvider, - isMember="MozMap") + isMember="Record") # While we have our inner type, set up our rooter, if needed if not isMember and typeNeedsRooting(returnType): - rooter = CGGeneric("MozMapRooter<%s> resultRooter(cx, &result);\n" % - result.define()) + rooter = CGGeneric("RecordRooter<%s> resultRooter(cx, &result);\n" % + ("nsString, " + result.define())) else: rooter = None - result = CGTemplatedType("MozMap", result) + result = CGTemplatedType("Record", [recordKeyDeclType(returnType), + result]) if nullable: result = CGTemplatedType("Nullable", result) return result, "ref", rooter, None, None @@ -7161,7 +7174,7 @@ class MethodNotNewObjectError(Exception): # nested sequences we don't use the same variable name to iterate over # different sequences. sequenceWrapLevel = 0 -mapWrapLevel = 0 +recordWrapLevel = 0 def wrapTypeIntoCurrentCompartment(type, value, isMember=True): @@ -7226,20 +7239,20 @@ def wrapTypeIntoCurrentCompartment(type, value, isMember=True): origType = type if type.nullable(): type = type.inner - mozMapRef = "%s.Value()" % value + recordRef = "%s.Value()" % value else: - mozMapRef = value - global mapWrapLevel - entryRef = "mapEntry%d" % mapWrapLevel - mapWrapLevel += 1 + recordRef = value + global recordWrapLevel + entryRef = "mapEntry%d" % recordWrapLevel + recordWrapLevel += 1 wrapElement = wrapTypeIntoCurrentCompartment(type.inner, "%s.mValue" % entryRef) - mapWrapLevel -= 1 + recordWrapLevel -= 1 if not wrapElement: return None wrapCode = CGWrapper(CGIndenter(wrapElement), pre=("for (auto& %s : %s.Entries()) {\n" % - (entryRef, mozMapRef)), + (entryRef, recordRef)), post="}\n") if origType.nullable(): wrapCode = CGIfWrapper(wrapCode, "!%s.IsNull()" % value) @@ -8131,7 +8144,7 @@ class CGMethodCall(CGThing): if distinguishingType(s).isSequence()) # Now append all the overloads that take a dictionary or callback - # interface or MozMap. There should be only one of these! + # interface or record. There should be only one of these! genericObjectSigs = [ s for s in possibleSignatures if (distinguishingType(s).isDictionary() or @@ -9694,13 +9707,18 @@ def getUnionAccessorSignatureType(type, descriptorProvider): if type.isSequence(): wrapperType = "Sequence" else: - wrapperType = "MozMap" + wrapperType = "Record" # We don't use the returned template here, so it's OK to just pass no # sourceDescription. elementInfo = getJSToNativeConversionInfo(type.inner, descriptorProvider, isMember=wrapperType) - return CGTemplatedType(wrapperType, elementInfo.declType, + if wrapperType == "Sequence": + innerType = elementInfo.declType + else: + innerType = [recordKeyDeclType(type), elementInfo.declType] + + return CGTemplatedType(wrapperType, innerType, isConst=True, isReference=True) # Nested unions are unwrapped automatically into our flatMemberTypes. @@ -10064,7 +10082,7 @@ class CGUnionStruct(CGThing): elif t.isRecord(): traceCases.append( CGCase("e" + vars["name"], - CGGeneric("TraceMozMap(trc, mValue.m%s.Value());\n" % + CGGeneric("TraceRecord(trc, mValue.m%s.Value());\n" % vars["name"]))) else: assert t.isSpiderMonkeyInterface() @@ -13194,7 +13212,7 @@ class CGDictionary(CGThing): if type.nullable(): trace = CGIfWrapper(trace, "!%s.IsNull()" % memberNullable) elif type.isRecord(): - # If you implement this, add a MozMap to + # If you implement this, add a record to # TestInterfaceJSDictionary and test it in test_bug1036214.html # to make sure we end up with the correct security properties. assert False @@ -14111,8 +14129,8 @@ class CGNativeMember(ClassMethod): returnCode = "aRetVal.SwapElements(${declName});\n" return "void", "", returnCode if type.isRecord(): - # If we want to handle MozMap-of-MozMap return values, we're - # going to need to fix example codegen to not produce MozMap + # If we want to handle record-of-record return values, we're + # going to need to fix example codegen to not produce record # for the relevant argument... assert not isMember # In this case we convert directly into our outparam to start with @@ -14166,7 +14184,8 @@ class CGNativeMember(ClassMethod): returnType = returnType.inner # And now the actual underlying type elementDecl = self.getReturnType(returnType.inner, True) - type = CGTemplatedType("MozMap", CGGeneric(elementDecl)) + type = CGTemplatedType("Record", [recordKeyDeclType(returnType), + CGGeneric(elementDecl)]) if nullable: type = CGTemplatedType("Nullable", type) args.append(Argument("%s&" % type.define(), "aRetVal")) @@ -14227,7 +14246,7 @@ class CGNativeMember(ClassMethod): Nullable as needed. isMember can be false or one of the strings "Sequence", "Variadic", - "MozMap" + "Record" """ if type.isSequence(): nullable = type.nullable() @@ -14243,8 +14262,8 @@ class CGNativeMember(ClassMethod): if nullable: type = type.inner elementType = type.inner - argType = self.getArgType(elementType, False, "MozMap")[0] - decl = CGTemplatedType("MozMap", argType) + argType = self.getArgType(elementType, False, "Record")[0] + decl = CGTemplatedType("Record", [recordKeyDeclType(type), argType]) return decl.define(), True, True if type.isUnion(): diff --git a/dom/bindings/MozMap.h b/dom/bindings/MozMap.h index 2725c74ff..2fe18be2b 100644 --- a/dom/bindings/MozMap.h +++ b/dom/bindings/MozMap.h @@ -5,11 +5,11 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ /** - * Class for representing MozMap arguments. Basically an array under the hood. + * Class for representing record arguments. Basically an array under the hood. */ -#ifndef mozilla_dom_MozMap_h -#define mozilla_dom_MozMap_h +#ifndef mozilla_dom_Record_h +#define mozilla_dom_Record_h #include "nsTHashtable.h" #include "nsHashKeys.h" @@ -23,15 +23,15 @@ namespace dom { namespace binding_detail { template -class MozMapEntry +class RecordEntry { public: - MozMapEntry() + RecordEntry() { } - // Move constructor so we can do MozMaps of MozMaps. - MozMapEntry(MozMapEntry&& aOther) + // Move constructor so we can do Records of Records. + RecordEntry(RecordEntry&& aOther) : mKey(Move(aOther.mKey)), mValue(Move(aOther.mValue)) { @@ -43,20 +43,19 @@ public: } // namespace binding_detail -template -class MozMap +template +class Record { public: - typedef nsString KeyType; - typedef typename binding_detail::MozMapEntry EntryType; - typedef MozMap SelfType; + typedef typename binding_detail::RecordEntry EntryType; + typedef Record SelfType; - MozMap() + Record() { } - // Move constructor so we can do MozMap of MozMap. - MozMap(SelfType&& aOther) : + // Move constructor so we can do Record of Record. + Record(SelfType&& aOther) : mEntries(Move(aOther.mEntries)) { } @@ -78,4 +77,4 @@ private: } // namespace dom } // namespace mozilla -#endif // mozilla_dom_MozMap_h +#endif // mozilla_dom_Record_h diff --git a/dom/bindings/moz.build b/dom/bindings/moz.build index f1ce9e276..7e1358e9c 100644 --- a/dom/bindings/moz.build +++ b/dom/bindings/moz.build @@ -32,10 +32,10 @@ EXPORTS.mozilla.dom += [ 'FakeString.h', 'IterableIterator.h', 'JSSlots.h', - 'MozMap.h', 'NonRefcountedDOMObject.h', 'Nullable.h', 'PrimitiveConversions.h', + 'Record.h', 'RootedDictionary.h', 'SimpleGlobalObject.h', 'StructuredClone.h', diff --git a/dom/fetch/Headers.h b/dom/fetch/Headers.h index 38b0fc68f..1dd92f779 100644 --- a/dom/fetch/Headers.h +++ b/dom/fetch/Headers.h @@ -20,7 +20,7 @@ class ErrorResult; namespace dom { -template class MozMap; +template class Record; class HeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord; class OwningHeadersOrByteStringSequenceSequenceOrByteStringByteStringRecord; diff --git a/dom/fetch/InternalHeaders.cpp b/dom/fetch/InternalHeaders.cpp index 83a686785..7bf5703dc 100644 --- a/dom/fetch/InternalHeaders.cpp +++ b/dom/fetch/InternalHeaders.cpp @@ -314,7 +314,7 @@ InternalHeaders::Fill(const Sequence>& aInit, ErrorResult& a } void -InternalHeaders::Fill(const MozMap& aInit, ErrorResult& aRv) +InternalHeaders::Fill(const Record& aInit, ErrorResult& aRv) { for (auto& entry : aInit.Entries()) { Append(NS_ConvertUTF16toUTF8(entry.mKey), entry.mValue, aRv); diff --git a/dom/fetch/InternalHeaders.h b/dom/fetch/InternalHeaders.h index 9a6d6dae7..98046f0ef 100644 --- a/dom/fetch/InternalHeaders.h +++ b/dom/fetch/InternalHeaders.h @@ -20,7 +20,7 @@ class ErrorResult; namespace dom { -template class MozMap; +template class Record; class HeadersEntry; class InternalHeaders final @@ -113,7 +113,7 @@ public: void Fill(const InternalHeaders& aInit, ErrorResult& aRv); void Fill(const Sequence>& aInit, ErrorResult& aRv); - void Fill(const MozMap& aInit, ErrorResult& aRv); + void Fill(const Record& aInit, ErrorResult& aRv); bool HasOnlySimpleHeaders() const; -- cgit v1.2.3 From 8525a292b0806d258576c2cfc5363b2c44dcaf22 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 20:07:10 +0200 Subject: Add ConvertJSValueTo*String functions that just take a value and hand out a string, without extra complications --- dom/bindings/BindingUtils.cpp | 10 +++++----- dom/bindings/BindingUtils.h | 30 ++++++++++++++++++++++++++++-- dom/bindings/Codegen.py | 2 +- 3 files changed, 34 insertions(+), 8 deletions(-) diff --git a/dom/bindings/BindingUtils.cpp b/dom/bindings/BindingUtils.cpp index 323feca52..8d2bdaac6 100644 --- a/dom/bindings/BindingUtils.cpp +++ b/dom/bindings/BindingUtils.cpp @@ -2558,7 +2558,7 @@ NonVoidByteStringToJsval(JSContext *cx, const nsACString &str, template static void -NormalizeUSVStringInternal(JSContext* aCx, T& aString) +NormalizeUSVStringInternal(T& aString) { char16_t* start = aString.BeginWriting(); // Must use const here because we can't pass char** to UTF16CharEnumerator as @@ -2575,15 +2575,15 @@ NormalizeUSVStringInternal(JSContext* aCx, T& aString) } void -NormalizeUSVString(JSContext* aCx, nsAString& aString) +NormalizeUSVString(nsAString& aString) { - NormalizeUSVStringInternal(aCx, aString); + NormalizeUSVStringInternal(aString); } void -NormalizeUSVString(JSContext* aCx, binding_detail::FakeString& aString) +NormalizeUSVString(binding_detail::FakeString& aString) { - NormalizeUSVStringInternal(aCx, aString); + NormalizeUSVStringInternal(aString); } bool diff --git a/dom/bindings/BindingUtils.h b/dom/bindings/BindingUtils.h index e017b986a..a3ec70f47 100644 --- a/dom/bindings/BindingUtils.h +++ b/dom/bindings/BindingUtils.h @@ -2127,11 +2127,30 @@ ConvertJSValueToString(JSContext* cx, JS::Handle v, return AssignJSString(cx, result, s); } +template +static inline bool +ConvertJSValueToString(JSContext* cx, JS::Handle v, T& result) +{ + return ConvertJSValueToString(cx, v, eStringify, eStringify, result); +} + void -NormalizeUSVString(JSContext* aCx, nsAString& aString); +NormalizeUSVString(nsAString& aString); void -NormalizeUSVString(JSContext* aCx, binding_detail::FakeString& aString); +NormalizeUSVString(binding_detail::FakeString& aString); + +template +static inline bool +ConvertJSValueToUSVString(JSContext* cx, JS::Handle v, T& result) +{ + if (!ConvertJSValueToString(cx, v, eStringify, eStringify, result)) { + return false; + } + + NormalizeUSVString(result); + return true; +} template inline bool @@ -2158,6 +2177,13 @@ bool ConvertJSValueToByteString(JSContext* cx, JS::Handle v, bool nullable, nsACString& result); +inline bool +ConvertJSValueToByteString(JSContext* cx, JS::Handle v, + nsACString& result) +{ + return ConvertJSValueToByteString(cx, v, false, result); +} + template void DoTraceSequence(JSTracer* trc, FallibleTArray& seq); template diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index ff6fa0ea3..915d7d431 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -5560,7 +5560,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, def getConversionCode(varName): normalizeCode = "" if type.isUSVString(): - normalizeCode = "NormalizeUSVString(cx, %s);\n" % varName + normalizeCode = "NormalizeUSVString(%s);\n" % varName conversionCode = fill(""" if (!ConvertJSValueToString(cx, $${val}, ${nullBehavior}, ${undefinedBehavior}, ${varName})) { -- cgit v1.2.3 From 66ee6fdde46bb9c246f7912fcc38d0883f66f961 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 20:13:17 +0200 Subject: Rename MozMap.h to Record.h --- dom/bindings/MozMap.h | 80 --------------------------------------------------- dom/bindings/Record.h | 80 +++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 80 insertions(+), 80 deletions(-) delete mode 100644 dom/bindings/MozMap.h create mode 100644 dom/bindings/Record.h diff --git a/dom/bindings/MozMap.h b/dom/bindings/MozMap.h deleted file mode 100644 index 2fe18be2b..000000000 --- a/dom/bindings/MozMap.h +++ /dev/null @@ -1,80 +0,0 @@ -/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* vim: set ts=8 sts=2 et sw=2 tw=80: */ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ - -/** - * Class for representing record arguments. Basically an array under the hood. - */ - -#ifndef mozilla_dom_Record_h -#define mozilla_dom_Record_h - -#include "nsTHashtable.h" -#include "nsHashKeys.h" -#include "nsStringGlue.h" -#include "nsTArray.h" -#include "mozilla/Attributes.h" -#include "mozilla/Move.h" - -namespace mozilla { -namespace dom { - -namespace binding_detail { -template -class RecordEntry -{ -public: - RecordEntry() - { - } - - // Move constructor so we can do Records of Records. - RecordEntry(RecordEntry&& aOther) - : mKey(Move(aOther.mKey)), - mValue(Move(aOther.mValue)) - { - } - - KeyType mKey; - ValueType mValue; -}; - -} // namespace binding_detail - -template -class Record -{ -public: - typedef typename binding_detail::RecordEntry EntryType; - typedef Record SelfType; - - Record() - { - } - - // Move constructor so we can do Record of Record. - Record(SelfType&& aOther) : - mEntries(Move(aOther.mEntries)) - { - } - - const nsTArray& Entries() const - { - return mEntries; - } - - nsTArray& Entries() - { - return mEntries; - } - -private: - nsTArray mEntries; -}; - -} // namespace dom -} // namespace mozilla - -#endif // mozilla_dom_Record_h diff --git a/dom/bindings/Record.h b/dom/bindings/Record.h new file mode 100644 index 000000000..2fe18be2b --- /dev/null +++ b/dom/bindings/Record.h @@ -0,0 +1,80 @@ +/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ +/* vim: set ts=8 sts=2 et sw=2 tw=80: */ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +/** + * Class for representing record arguments. Basically an array under the hood. + */ + +#ifndef mozilla_dom_Record_h +#define mozilla_dom_Record_h + +#include "nsTHashtable.h" +#include "nsHashKeys.h" +#include "nsStringGlue.h" +#include "nsTArray.h" +#include "mozilla/Attributes.h" +#include "mozilla/Move.h" + +namespace mozilla { +namespace dom { + +namespace binding_detail { +template +class RecordEntry +{ +public: + RecordEntry() + { + } + + // Move constructor so we can do Records of Records. + RecordEntry(RecordEntry&& aOther) + : mKey(Move(aOther.mKey)), + mValue(Move(aOther.mValue)) + { + } + + KeyType mKey; + ValueType mValue; +}; + +} // namespace binding_detail + +template +class Record +{ +public: + typedef typename binding_detail::RecordEntry EntryType; + typedef Record SelfType; + + Record() + { + } + + // Move constructor so we can do Record of Record. + Record(SelfType&& aOther) : + mEntries(Move(aOther.mEntries)) + { + } + + const nsTArray& Entries() const + { + return mEntries; + } + + nsTArray& Entries() + { + return mEntries; + } + +private: + nsTArray mEntries; +}; + +} // namespace dom +} // namespace mozilla + +#endif // mozilla_dom_Record_h -- cgit v1.2.3 From e7c9fa3e1505aeb90385e0a4e90fe5e0b137d4ab Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 20:17:36 +0200 Subject: Actually change the key type of a record, and its corresponding conversion behavior, depending on what the IDL says --- dom/bindings/Codegen.py | 48 +++++++++++++++++++++++++++++++++++-------- dom/bindings/Record.h | 2 +- dom/fetch/InternalHeaders.cpp | 2 +- 3 files changed, 41 insertions(+), 11 deletions(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index 915d7d431..4e6248e49 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4372,11 +4372,15 @@ def handleDefaultStringValue(defaultValue, method): } -def recordKeyDeclType(recordType): +def recordKeyType(recordType): assert recordType.keyType.isString() if recordType.keyType.isByteString(): - return CGGeneric("nsCString") - return CGGeneric("nsString") + return "nsCString" + return "nsString" + + +def recordKeyDeclType(recordType): + return CGGeneric(recordKeyType(recordType)) # If this function is modified, modify CGNativeMember.getArg and @@ -4786,6 +4790,15 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, "passedToJSImpl": "${passedToJSImpl}" }) + keyType = recordKeyType(recordType) + if recordType.keyType.isDOMString(): + keyConversionFunction = "ConvertJSValueToString" + elif recordType.keyType.isUSVString(): + keyConversionFunction = "ConvertJSValueToUSVString" + else: + assert recordType.keyType.isByteString() + keyConversionFunction = "ConvertJSValueToByteString" + templateBody = fill( """ auto& recordEntries = ${recordRef}.Entries(); @@ -4805,6 +4818,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, JS::Rooted propNameValue(cx); JS::Rooted temp(cx); JS::Rooted curId(cx); + JS::Rooted idVal(cx); for (size_t i = 0; i < ids.length(); ++i) { curId = ids[i]; @@ -4821,12 +4835,11 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, continue; } - binding_detail::FakeString propName; - bool isSymbol; - if (!ConvertIdToString(cx, curId, propName, isSymbol)) { + idVal = js::IdToValue(curId); + ${keyType} propName; + if (!${keyConversionFunction}(cx, idVal, propName)) { $*{exceptionCode} } - MOZ_ASSERT(!isSymbol, "We said, no symbols!"); if (!JS_GetPropertyById(cx, recordObj, curId, &temp)) { $*{exceptionCode} @@ -4842,6 +4855,8 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, """, exceptionCode=exceptionCode, recordRef=recordRef, + keyType=keyType, + keyConversionFunction=keyConversionFunction, typeName=typeName, valueType=valueInfo.declType.define(), valueConversion=valueConversion) @@ -6491,6 +6506,18 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, 'typedArraysAreStructs': typedArraysAreStructs }) recordWrapLevel -= 1 + if type.keyType.isByteString(): + # There is no length-taking JS_DefineProperty. So to keep + # things sane with embedded nulls, we want to byte-inflate + # to an nsAString. The only byte-inflation function we + # have around is AppendASCIItoUTF16, which luckily doesn't + # assert anything about the input being ASCII. + expandedKeyDecl = "NS_ConvertASCIItoUTF16 expandedKey(entry.mKey);\n" + keyName = "expandedKey" + else: + expandedKeyDecl = "" + keyName = "entry.mKey" + code = fill( """ @@ -6508,9 +6535,10 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, do { $*{innerTemplate} } while (0); + $*{expandedKeyDecl} if (!JS_DefineUCProperty(cx, returnObj, - entry.mKey.BeginReading(), - entry.mKey.Length(), tmp, + ${keyName}.BeginReading(), + ${keyName}.Length(), tmp, JSPROP_ENUMERATE)) { $*{exceptionCode} } @@ -6522,6 +6550,8 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode, exceptionCode=exceptionCode, valueName=valueName, innerTemplate=innerTemplate, + expandedKeyDecl=expandedKeyDecl, + keyName=keyName, set=setObject("*returnObj")) return (code, False) diff --git a/dom/bindings/Record.h b/dom/bindings/Record.h index 2fe18be2b..b7f7b01b0 100644 --- a/dom/bindings/Record.h +++ b/dom/bindings/Record.h @@ -47,7 +47,7 @@ template class Record { public: - typedef typename binding_detail::RecordEntry EntryType; + typedef typename binding_detail::RecordEntry EntryType; typedef Record SelfType; Record() diff --git a/dom/fetch/InternalHeaders.cpp b/dom/fetch/InternalHeaders.cpp index 7bf5703dc..f66221d42 100644 --- a/dom/fetch/InternalHeaders.cpp +++ b/dom/fetch/InternalHeaders.cpp @@ -317,7 +317,7 @@ void InternalHeaders::Fill(const Record& aInit, ErrorResult& aRv) { for (auto& entry : aInit.Entries()) { - Append(NS_ConvertUTF16toUTF8(entry.mKey), entry.mValue, aRv); + Append(entry.mKey, entry.mValue, aRv); if (aRv.Failed()) { return; } -- cgit v1.2.3 From ca23830127a2123100e52e644302e23143d8369a Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 20:19:53 +0200 Subject: Implement the spec provision for handling repeated keys in records by updating the existing value --- dom/bindings/Codegen.py | 44 +++++++++++++++++++++++++++++++++++--------- dom/bindings/Record.h | 11 +++++++++++ 2 files changed, 46 insertions(+), 9 deletions(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index 4e6248e49..e32d16a48 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4791,13 +4791,16 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, }) keyType = recordKeyType(recordType) - if recordType.keyType.isDOMString(): - keyConversionFunction = "ConvertJSValueToString" - elif recordType.keyType.isUSVString(): - keyConversionFunction = "ConvertJSValueToUSVString" - else: - assert recordType.keyType.isByteString() + if recordType.keyType.isByteString(): keyConversionFunction = "ConvertJSValueToByteString" + hashKeyType = "nsCStringHashKey" + else: + hashKeyType = "nsStringHashKey" + if recordType.keyType.isDOMString(): + keyConversionFunction = "ConvertJSValueToString" + else: + assert recordType.keyType.isUSVString() + keyConversionFunction = "ConvertJSValueToUSVString" templateBody = fill( """ @@ -4819,6 +4822,12 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, JS::Rooted temp(cx); JS::Rooted curId(cx); JS::Rooted idVal(cx); + // Use a hashset to keep track of ids seen, to avoid + // introducing nasty O(N^2) behavior scanning for them all the + // time. Ideally we'd use a data structure with O(1) lookup + // _and_ ordering for the MozMap, but we don't have one lying + // around. + nsTHashtable<${hashKeyType}> idsSeen; for (size_t i = 0; i < ids.length(); ++i) { curId = ids[i]; @@ -4845,9 +4854,25 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, $*{exceptionCode} } - // Safe to do an infallible append here, because we did a - // SetCapacity above to the right capacity. - ${typeName}::EntryType* entry = recordEntries.AppendElement(); + ${typeName}::EntryType* entry; + if (idsSeen.Contains(propName)) { + // Find the existing entry. + auto idx = recordEntries.IndexOf(propName); + MOZ_ASSERT(idx != recordEntries.NoIndex, + "Why is it not found?"); + // Now blow it away to make it look like it was just added + // to the array, because it's not obvious that it's + // safe to write to its already-initialized mValue via our + // normal codegen conversions. For example, the value + // could be a union and this would change its type, but + // codegen assumes we won't do that. + entry = recordEntries.ReconstructElementAt(idx); + } else { + // Safe to do an infallible append here, because we did a + // SetCapacity above to the right capacity. + entry = recordEntries.AppendElement(); + idsSeen.PutEntry(propName); + } entry->mKey = propName; ${valueType}& slot = entry->mValue; $*{valueConversion} @@ -4855,6 +4880,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, """, exceptionCode=exceptionCode, recordRef=recordRef, + hashKeyType=hashKeyType, keyType=keyType, keyConversionFunction=keyConversionFunction, typeName=typeName, diff --git a/dom/bindings/Record.h b/dom/bindings/Record.h index b7f7b01b0..d6ab31699 100644 --- a/dom/bindings/Record.h +++ b/dom/bindings/Record.h @@ -77,4 +77,15 @@ private: } // namespace dom } // namespace mozilla +template +class nsDefaultComparator, K> +{ +public: + bool Equals(const mozilla::dom::binding_detail::RecordEntry& aEntry, + const K& aKey) const + { + return aEntry.mKey == aKey; + } +}; + #endif // mozilla_dom_Record_h -- cgit v1.2.3 From 04c16841227708a6037acb14ba506f0981481e37 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 21:20:12 +0200 Subject: Construct URLSearchParams from sequence or from string --- dom/url/URLSearchParams.cpp | 45 +++++++++++++++++---------------------- dom/url/URLSearchParams.h | 19 +++-------------- dom/webidl/URLSearchParams.webidl | 3 +-- 3 files changed, 24 insertions(+), 43 deletions(-) diff --git a/dom/url/URLSearchParams.cpp b/dom/url/URLSearchParams.cpp index d9492f81c..8303272e1 100644 --- a/dom/url/URLSearchParams.cpp +++ b/dom/url/URLSearchParams.cpp @@ -314,14 +314,6 @@ URLSearchParams::URLSearchParams(nsISupports* aParent, { } -URLSearchParams::URLSearchParams(nsISupports* aParent, - const URLSearchParams& aOther) - : mParams(new URLParams(*aOther.mParams.get())) - , mParent(aParent) - , mObserver(nullptr) -{ -} - URLSearchParams::~URLSearchParams() { DeleteAll(); @@ -335,34 +327,37 @@ URLSearchParams::WrapObject(JSContext* aCx, JS::Handle aGivenProto) /* static */ already_AddRefed URLSearchParams::Constructor(const GlobalObject& aGlobal, - const nsAString& aInit, + const USVStringSequenceSequenceOrUSVString& aInit, ErrorResult& aRv) { RefPtr sp = new URLSearchParams(aGlobal.GetAsSupports(), nullptr); - NS_ConvertUTF16toUTF8 input(aInit); - - if (StringBeginsWith(input, NS_LITERAL_CSTRING("?"))) { - sp->ParseInput(Substring(input, 1, input.Length() - 1)); + if (aInit.IsUSVString()) { + NS_ConvertUTF16toUTF8 input(aInit.GetAsUSVString()); + if (StringBeginsWith(input, NS_LITERAL_CSTRING("?"))) { + sp->ParseInput(Substring(input, 1, input.Length() - 1)); + } else { + sp->ParseInput(input); + } + } else if (aInit.IsUSVStringSequenceSequence()) { + const Sequence>& list = + aInit.GetAsUSVStringSequenceSequence(); + for (uint32_t i = 0; i < list.Length(); ++i) { + const Sequence& item = list[i]; + if (item.Length() != 2) { + aRv.Throw(NS_ERROR_DOM_TYPE_ERR); + return nullptr; + } + sp->Append(item[0], item[1]); + } } else { - sp->ParseInput(input); + MOZ_CRASH("This should not happen."); } return sp.forget(); } -/* static */ already_AddRefed -URLSearchParams::Constructor(const GlobalObject& aGlobal, - URLSearchParams& aInit, - ErrorResult& aRv) -{ - RefPtr sp = - new URLSearchParams(aGlobal.GetAsSupports(), aInit); - - return sp.forget(); -} - void URLSearchParams::ParseInput(const nsACString& aInput) { diff --git a/dom/url/URLSearchParams.h b/dom/url/URLSearchParams.h index 4b0aaa991..5eef1b1a9 100644 --- a/dom/url/URLSearchParams.h +++ b/dom/url/URLSearchParams.h @@ -20,6 +20,7 @@ namespace mozilla { namespace dom { class URLSearchParams; +class USVStringSequenceSequenceOrUSVString; class URLSearchParamsObserver : public nsISupports { @@ -43,14 +44,6 @@ public: DeleteAll(); } - explicit URLParams(const URLParams& aOther) - : mParams(aOther.mParams) - {} - - URLParams(const URLParams&& aOther) - : mParams(Move(aOther.mParams)) - {} - class ForEachIterator { public: @@ -144,9 +137,6 @@ public: explicit URLSearchParams(nsISupports* aParent, URLSearchParamsObserver* aObserver=nullptr); - URLSearchParams(nsISupports* aParent, - const URLSearchParams& aOther); - // WebIDL methods nsISupports* GetParentObject() const { @@ -157,11 +147,8 @@ public: WrapObject(JSContext* aCx, JS::Handle aGivenProto) override; static already_AddRefed - Constructor(const GlobalObject& aGlobal, const nsAString& aInit, - ErrorResult& aRv); - - static already_AddRefed - Constructor(const GlobalObject& aGlobal, URLSearchParams& aInit, + Constructor(const GlobalObject& aGlobal, + const USVStringSequenceSequenceOrUSVString& aInit, ErrorResult& aRv); void ParseInput(const nsACString& aInput); diff --git a/dom/webidl/URLSearchParams.webidl b/dom/webidl/URLSearchParams.webidl index 93e846071..e44565654 100644 --- a/dom/webidl/URLSearchParams.webidl +++ b/dom/webidl/URLSearchParams.webidl @@ -13,8 +13,7 @@ * http://www.openwebfoundation.org/legal/the-owf-1-0-agreements/owfa-1-0. */ -[Constructor(optional USVString init = ""), - Constructor(URLSearchParams init), +[Constructor(optional (sequence> or USVString) init = ""), Exposed=(Window,Worker,WorkerDebugger,System)] interface URLSearchParams { void append(USVString name, USVString value); -- cgit v1.2.3 From cd0e94ceb1031a76dc8e9f70bb9cdab691fb8866 Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 21:22:29 +0200 Subject: Construct URLSearchParams from record<> --- dom/url/URLSearchParams.cpp | 8 +++++++- dom/url/URLSearchParams.h | 4 ++-- dom/webidl/URLSearchParams.webidl | 2 +- 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/dom/url/URLSearchParams.cpp b/dom/url/URLSearchParams.cpp index 8303272e1..ad23460f3 100644 --- a/dom/url/URLSearchParams.cpp +++ b/dom/url/URLSearchParams.cpp @@ -327,7 +327,7 @@ URLSearchParams::WrapObject(JSContext* aCx, JS::Handle aGivenProto) /* static */ already_AddRefed URLSearchParams::Constructor(const GlobalObject& aGlobal, - const USVStringSequenceSequenceOrUSVString& aInit, + const USVStringSequenceSequenceOrUSVStringUSVStringRecordOrUSVString& aInit, ErrorResult& aRv) { RefPtr sp = @@ -351,6 +351,12 @@ URLSearchParams::Constructor(const GlobalObject& aGlobal, } sp->Append(item[0], item[1]); } + } else if (aInit.IsUSVStringUSVStringRecord()) { + const Record& record = + aInit.GetAsUSVStringUSVStringRecord(); + for (auto& entry : record.Entries()) { + sp->Append(entry.mKey, entry.mValue); + } } else { MOZ_CRASH("This should not happen."); } diff --git a/dom/url/URLSearchParams.h b/dom/url/URLSearchParams.h index 5eef1b1a9..9fefd78dd 100644 --- a/dom/url/URLSearchParams.h +++ b/dom/url/URLSearchParams.h @@ -20,7 +20,7 @@ namespace mozilla { namespace dom { class URLSearchParams; -class USVStringSequenceSequenceOrUSVString; +class USVStringSequenceSequenceOrUSVStringUSVStringRecordOrUSVString; class URLSearchParamsObserver : public nsISupports { @@ -148,7 +148,7 @@ public: static already_AddRefed Constructor(const GlobalObject& aGlobal, - const USVStringSequenceSequenceOrUSVString& aInit, + const USVStringSequenceSequenceOrUSVStringUSVStringRecordOrUSVString& aInit, ErrorResult& aRv); void ParseInput(const nsACString& aInput); diff --git a/dom/webidl/URLSearchParams.webidl b/dom/webidl/URLSearchParams.webidl index e44565654..b93f4e8b1 100644 --- a/dom/webidl/URLSearchParams.webidl +++ b/dom/webidl/URLSearchParams.webidl @@ -13,7 +13,7 @@ * http://www.openwebfoundation.org/legal/the-owf-1-0-agreements/owfa-1-0. */ -[Constructor(optional (sequence> or USVString) init = ""), +[Constructor(optional (sequence> or record or USVString) init = ""), Exposed=(Window,Worker,WorkerDebugger,System)] interface URLSearchParams { void append(USVString name, USVString value); -- cgit v1.2.3 From c00255c355ab32f7b19f21e9797a8fb83827d0be Mon Sep 17 00:00:00 2001 From: JustOff Date: Wed, 13 Mar 2019 21:44:49 +0200 Subject: Align IDL record to C++ conversion with the spec when Symbol-named properties are involved --- dom/bindings/Codegen.py | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/dom/bindings/Codegen.py b/dom/bindings/Codegen.py index e32d16a48..74acb5918 100644 --- a/dom/bindings/Codegen.py +++ b/dom/bindings/Codegen.py @@ -4808,10 +4808,8 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, JS::Rooted recordObj(cx, &$${val}.toObject()); JS::AutoIdVector ids(cx); - // Keep skipping symbols until - // https://github.com/heycam/webidl/issues/294 is sorted out. if (!js::GetPropertyKeys(cx, recordObj, - JSITER_OWNONLY | JSITER_HIDDEN, &ids)) { + JSITER_OWNONLY | JSITER_HIDDEN | JSITER_SYMBOLS, &ids)) { $*{exceptionCode} } if (!recordEntries.SetCapacity(ids.length(), mozilla::fallible)) { @@ -4831,8 +4829,6 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, for (size_t i = 0; i < ids.length(); ++i) { curId = ids[i]; - MOZ_ASSERT(!JSID_IS_SYMBOL(curId), "No symbols, we said!"); - JS::Rooted desc(cx); if (!JS_GetOwnPropertyDescriptorById(cx, recordObj, curId, &desc)) { @@ -4846,6 +4842,8 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None, idVal = js::IdToValue(curId); ${keyType} propName; + // This will just throw if idVal is a Symbol, like the spec says + // to do. if (!${keyConversionFunction}(cx, idVal, propName)) { $*{exceptionCode} } -- cgit v1.2.3 From 0b4184ad359d635bb47ac526d4675e931e2fdeea Mon Sep 17 00:00:00 2001 From: wolfbeast Date: Thu, 14 Mar 2019 09:01:12 +0100 Subject: [Palemoon] Disable Microsoft Family Safety support (Windows 8.1). This is basically a https MitM setup that is unwanted for Pale Moon. Resolves #1000. --- application/palemoon/app/profile/palemoon.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/application/palemoon/app/profile/palemoon.js b/application/palemoon/app/profile/palemoon.js index 3df5d7194..85dc41c15 100644 --- a/application/palemoon/app/profile/palemoon.js +++ b/application/palemoon/app/profile/palemoon.js @@ -1121,6 +1121,9 @@ pref("security.csp.speccompliant", true); // Block insecure active content on https pages pref("security.mixed_content.block_active_content", true); +// Disable Microsoft Family Safety MitM support +pref("security.family_safety.mode", 0); + // Override the Gecko-default value of false for Pale Moon. pref("plain_text.wrap_long_lines", true); -- cgit v1.2.3 From d791dfed61bbc963351e5965657a3b13d4e6dceb Mon Sep 17 00:00:00 2001 From: wolfbeast Date: Thu, 14 Mar 2019 13:07:00 +0100 Subject: Remove unused SSL errorReporting prefs Resolves #1003. --- netwerk/base/security-prefs.js | 4 ---- 1 file changed, 4 deletions(-) diff --git a/netwerk/base/security-prefs.js b/netwerk/base/security-prefs.js index ea0b2236d..ef78ddccb 100644 --- a/netwerk/base/security-prefs.js +++ b/netwerk/base/security-prefs.js @@ -117,10 +117,6 @@ pref("security.webauth.u2f", false); pref("security.webauth.u2f_enable_softtoken", false); pref("security.webauth.u2f_enable_usbtoken", false); -pref("security.ssl.errorReporting.enabled", true); -pref("security.ssl.errorReporting.url", "https://incoming.telemetry.mozilla.org/submit/sslreports/"); -pref("security.ssl.errorReporting.automatic", false); - // OCSP must-staple pref("security.ssl.enable_ocsp_must_staple", true); -- cgit v1.2.3 From 0ff4dbff80ddea637b0fb02c885e222ddcfa171a Mon Sep 17 00:00:00 2001 From: JustOff Date: Thu, 14 Mar 2019 14:14:45 +0200 Subject: Use meaningful error message in URLSearchParams::Constructor --- dom/url/URLSearchParams.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dom/url/URLSearchParams.cpp b/dom/url/URLSearchParams.cpp index ad23460f3..f762299f8 100644 --- a/dom/url/URLSearchParams.cpp +++ b/dom/url/URLSearchParams.cpp @@ -358,7 +358,7 @@ URLSearchParams::Constructor(const GlobalObject& aGlobal, sp->Append(entry.mKey, entry.mValue); } } else { - MOZ_CRASH("This should not happen."); + MOZ_CRASH("URLSearchParams: Invalid string"); } return sp.forget(); -- cgit v1.2.3 From 6e457e653e5c4b2a92a2a7adc1ea6bcdc2d39a5f Mon Sep 17 00:00:00 2001 From: adeshkp Date: Thu, 14 Mar 2019 09:49:51 -0400 Subject: Fix a warning about method override --- dom/ipc/ContentChild.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/dom/ipc/ContentChild.h b/dom/ipc/ContentChild.h index f29d17e7f..4c8f15cc0 100644 --- a/dom/ipc/ContentChild.h +++ b/dom/ipc/ContentChild.h @@ -152,13 +152,13 @@ public: RecvInitRendering( Endpoint&& aCompositor, Endpoint&& aImageBridge, - Endpoint&& aVideoManager); + Endpoint&& aVideoManager) override; bool RecvReinitRendering( Endpoint&& aCompositor, Endpoint&& aImageBridge, - Endpoint&& aVideoManager); + Endpoint&& aVideoManager) override; PProcessHangMonitorChild* AllocPProcessHangMonitorChild(Transport* aTransport, -- cgit v1.2.3 From 52be954e59b3ef06b7e8bfa28630e1005351d183 Mon Sep 17 00:00:00 2001 From: adeshkp Date: Thu, 14 Mar 2019 09:52:03 -0400 Subject: Fix order of member variables in a couple of initializer lists --- image/imgFrame.cpp | 2 +- security/manager/ssl/nsSiteSecurityService.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/image/imgFrame.cpp b/image/imgFrame.cpp index c9f44181d..d982c17c4 100644 --- a/image/imgFrame.cpp +++ b/image/imgFrame.cpp @@ -161,13 +161,13 @@ imgFrame::imgFrame() : mMonitor("imgFrame") , mDecoded(0, 0, 0, 0) , mLockCount(0) + , mHasNoAlpha(false) , mAborted(false) , mFinished(false) , mOptimizable(false) , mTimeout(FrameTimeout::FromRawMilliseconds(100)) , mDisposalMethod(DisposalMethod::NOT_SPECIFIED) , mBlendMethod(BlendMethod::OVER) - , mHasNoAlpha(false) , mPalettedImageData(nullptr) , mPaletteDepth(0) , mNonPremult(false) diff --git a/security/manager/ssl/nsSiteSecurityService.cpp b/security/manager/ssl/nsSiteSecurityService.cpp index fc38f4e64..cfee79d8d 100644 --- a/security/manager/ssl/nsSiteSecurityService.cpp +++ b/security/manager/ssl/nsSiteSecurityService.cpp @@ -210,8 +210,8 @@ const uint64_t kSixtyDaysInSeconds = 60 * 24 * 60 * 60; nsSiteSecurityService::nsSiteSecurityService() : mMaxMaxAge(kSixtyDaysInSeconds) , mUsePreloadList(true) - , mPreloadListTimeOffset(0) , mUseStsService(true) + , mPreloadListTimeOffset(0) { } -- cgit v1.2.3 From 90d1ee25b1de235847605fbc95a9ddebcf5c061d Mon Sep 17 00:00:00 2001 From: adeshkp Date: Thu, 14 Mar 2019 09:53:02 -0400 Subject: Remove a couple of unused variables --- js/src/jit/StupidAllocator.cpp | 1 - js/src/vm/ObjectGroup.cpp | 1 - 2 files changed, 2 deletions(-) diff --git a/js/src/jit/StupidAllocator.cpp b/js/src/jit/StupidAllocator.cpp index 8e3ea6286..55431e8e0 100644 --- a/js/src/jit/StupidAllocator.cpp +++ b/js/src/jit/StupidAllocator.cpp @@ -407,7 +407,6 @@ StupidAllocator::allocateForDefinition(LInstruction* ins, LDefinition* def) { uint32_t vreg = def->virtualRegister(); - CodePosition from; if ((def->output()->isRegister() && def->policy() == LDefinition::FIXED) || def->policy() == LDefinition::MUST_REUSE_INPUT) { diff --git a/js/src/vm/ObjectGroup.cpp b/js/src/vm/ObjectGroup.cpp index 1fbf8976b..46159a972 100644 --- a/js/src/vm/ObjectGroup.cpp +++ b/js/src/vm/ObjectGroup.cpp @@ -495,7 +495,6 @@ ObjectGroup::defaultNewGroup(ExclusiveContext* cx, const Class* clasp, if (associated->is()) { // Canonicalize new functions to use the original one associated with its script. - JSFunction* fun = &associated->as(); associated = associated->as().maybeCanonicalFunction(); // If we have previously cleared the 'new' script information for this -- cgit v1.2.3 From cf36d986290114b6dd1fcdac6c08283178629742 Mon Sep 17 00:00:00 2001 From: adeshkp Date: Thu, 14 Mar 2019 09:54:30 -0400 Subject: Fix warnings about unreachable code in cubeb --- media/libcubeb/src/cubeb.c | 2 +- media/libcubeb/src/cubeb_audiounit.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/media/libcubeb/src/cubeb.c b/media/libcubeb/src/cubeb.c index e0375c394..eb22a9b94 100644 --- a/media/libcubeb/src/cubeb.c +++ b/media/libcubeb/src/cubeb.c @@ -562,7 +562,7 @@ int cubeb_set_log_callback(cubeb_log_level log_level, void cubeb_crash() { - abort(); *((volatile int *) NULL) = 0; + abort(); } diff --git a/media/libcubeb/src/cubeb_audiounit.cpp b/media/libcubeb/src/cubeb_audiounit.cpp index f24dfbff2..9483c2795 100644 --- a/media/libcubeb/src/cubeb_audiounit.cpp +++ b/media/libcubeb/src/cubeb_audiounit.cpp @@ -1443,12 +1443,12 @@ audiounit_set_buffer_size(cubeb_stream * stm, uint32_t new_size_frames, set_buff buffer_size_changed_callback, stm); if (r != noErr) { - return CUBEB_ERROR; if (set_side == INPUT) { PRINT_ERROR_CODE("AudioUnitAddPropertyListener/input/kAudioDevicePropertyBufferFrameSize", r); } else { PRINT_ERROR_CODE("AudioUnitAddPropertyListener/output/kAudioDevicePropertyBufferFrameSize", r); } + return CUBEB_ERROR; } if (!stm->buffer_size_change_state && count >= 30) { -- cgit v1.2.3 From 4d7390eaaae4456775a3614ee20a75d01f8f1074 Mon Sep 17 00:00:00 2001 From: JustOff Date: Thu, 14 Mar 2019 17:42:08 +0200 Subject: [PALEMOON] Add SSUAO override for firefox.com (native mode) --- application/palemoon/branding/shared/pref/uaoverrides.inc | 1 + 1 file changed, 1 insertion(+) diff --git a/application/palemoon/branding/shared/pref/uaoverrides.inc b/application/palemoon/branding/shared/pref/uaoverrides.inc index 567956640..3e28225f4 100644 --- a/application/palemoon/branding/shared/pref/uaoverrides.inc +++ b/application/palemoon/branding/shared/pref/uaoverrides.inc @@ -63,6 +63,7 @@ pref("@GUAO_PREF@.deviantart.com","Mozilla/5.0 (@OS_SLICE@ rv:@GRE_VERSION@) @GR pref("@GUAO_PREF@.deviantart.net","Mozilla/5.0 (@OS_SLICE@ rv:@GRE_VERSION@) @GRE_DATE_SLICE@ @PM_SLICE@"); pref("@GUAO_PREF@.altibox.dk","Mozilla/5.0 (@OS_SLICE@ rv:@GRE_VERSION@) @GRE_DATE_SLICE@ @PM_SLICE@"); pref("@GUAO_PREF@.altibox.no","Mozilla/5.0 (@OS_SLICE@ rv:@GRE_VERSION@) @GRE_DATE_SLICE@ @PM_SLICE@"); +pref("@GUAO_PREF@.firefox.com","Mozilla/5.0 (@OS_SLICE@ rv:@GRE_VERSION@) @GRE_DATE_SLICE@ @PM_SLICE@"); // UA-Sniffing domains below have indicated no interest in supporting Pale Moon (BOO!) pref("@GUAO_PREF@.humblebundle.com","Mozilla/5.0 (@OS_SLICE@ rv:@GK_VERSION@) @GK_SLICE@ @FX_SLICE@ (Pale Moon)"); -- cgit v1.2.3 From c427cf64a8c13b13ce39fecf9db71672df622038 Mon Sep 17 00:00:00 2001 From: JustOff Date: Thu, 14 Mar 2019 19:40:42 +0200 Subject: Handle the special case of a flex frame being the absolute containing block correctly from the CSS align code --- layout/generic/nsAbsoluteContainingBlock.cpp | 28 ++++++++++++---- ...position-absolute-containing-block-001-ref.html | 27 +++++++++++++++ .../position-absolute-containing-block-001.html | 30 +++++++++++++++++ ...position-absolute-containing-block-002-ref.html | 27 +++++++++++++++ .../position-absolute-containing-block-002.html | 38 ++++++++++++++++++++++ .../w3c-css/submitted/flexbox/reftest.list | 4 +++ 6 files changed, 148 insertions(+), 6 deletions(-) create mode 100644 layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001-ref.html create mode 100644 layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001.html create mode 100644 layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002-ref.html create mode 100644 layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002.html diff --git a/layout/generic/nsAbsoluteContainingBlock.cpp b/layout/generic/nsAbsoluteContainingBlock.cpp index 7c48aae92..e3c847d01 100644 --- a/layout/generic/nsAbsoluteContainingBlock.cpp +++ b/layout/generic/nsAbsoluteContainingBlock.cpp @@ -409,14 +409,30 @@ OffsetToAlignedStaticPos(const ReflowInput& aKidReflowInput, ? GetOrthogonalAxis(aAbsPosCBAxis) : aAbsPosCBAxis); + const bool placeholderContainerIsContainingBlock = + aPlaceholderContainer == aKidReflowInput.mCBReflowInput->mFrame; + nsIAtom* parentType = aPlaceholderContainer->GetType(); LogicalSize alignAreaSize(pcWM); if (parentType == nsGkAtoms::flexContainerFrame) { - // The alignment container is the flex container's content box: - alignAreaSize = aPlaceholderContainer->GetLogicalSize(pcWM); - LogicalMargin pcBorderPadding = - aPlaceholderContainer->GetLogicalUsedBorderAndPadding(pcWM); - alignAreaSize -= pcBorderPadding.Size(pcWM); + // We store the frame rect in FinishAndStoreOverflow, which runs _after_ + // reflowing the absolute frames, so handle the special case of the frame + // being the actual containing block here, by getting the size from + // aAbsPosCBSize. + // + // The alignment container is the flex container's content box. + if (placeholderContainerIsContainingBlock) { + alignAreaSize = aAbsPosCBSize.ConvertTo(pcWM, aAbsPosCBWM); + // aAbsPosCBSize is the padding-box, so substract the padding to get the + // content box. + alignAreaSize -= + aPlaceholderContainer->GetLogicalUsedPadding(pcWM).Size(pcWM); + } else { + alignAreaSize = aPlaceholderContainer->GetLogicalSize(pcWM); + LogicalMargin pcBorderPadding = + aPlaceholderContainer->GetLogicalUsedBorderAndPadding(pcWM); + alignAreaSize -= pcBorderPadding.Size(pcWM); + } } else if (parentType == nsGkAtoms::gridContainerFrame) { // This abspos elem's parent is a grid container. Per CSS Grid 10.1 & 10.2: // - If the grid container *also* generates the abspos containing block (a @@ -424,7 +440,7 @@ OffsetToAlignedStaticPos(const ReflowInput& aKidReflowInput, // the alignment container, too. (And its size is aAbsPosCBSize.) // - Otherwise, we use the grid's padding box as the alignment container. // https://drafts.csswg.org/css-grid/#static-position - if (aPlaceholderContainer == aKidReflowInput.mCBReflowInput->mFrame) { + if (placeholderContainerIsContainingBlock) { // The alignment container is the grid area that we're using as the // absolute containing block. alignAreaSize = aAbsPosCBSize.ConvertTo(pcWM, aAbsPosCBWM); diff --git a/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001-ref.html b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001-ref.html new file mode 100644 index 000000000..08eec8691 --- /dev/null +++ b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001-ref.html @@ -0,0 +1,27 @@ + + +CSS Test Reference + + + +
+ \ No newline at end of file diff --git a/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001.html b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001.html new file mode 100644 index 000000000..5f623cb84 --- /dev/null +++ b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-001.html @@ -0,0 +1,30 @@ + + +CSS Test: Absolutely positioned children of flex container with CSS align + + + + + + +
+ \ No newline at end of file diff --git a/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002-ref.html b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002-ref.html new file mode 100644 index 000000000..df730047b --- /dev/null +++ b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002-ref.html @@ -0,0 +1,27 @@ + + +CSS Test Reference + + + +
+ \ No newline at end of file diff --git a/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002.html b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002.html new file mode 100644 index 000000000..9e89c5ad0 --- /dev/null +++ b/layout/reftests/w3c-css/submitted/flexbox/position-absolute-containing-block-002.html @@ -0,0 +1,38 @@ + + +CSS Test: Absolutely positioned children of flex container with CSS align + + + + + + +
+ \ No newline at end of file diff --git a/layout/reftests/w3c-css/submitted/flexbox/reftest.list b/layout/reftests/w3c-css/submitted/flexbox/reftest.list index fd8bfccc9..3df75aee6 100644 --- a/layout/reftests/w3c-css/submitted/flexbox/reftest.list +++ b/layout/reftests/w3c-css/submitted/flexbox/reftest.list @@ -211,3 +211,7 @@ fails == flexbox-min-height-auto-002b.html flexbox-min-height-auto-002-ref.html == flexbox-single-line-clamp-1.html flexbox-single-line-clamp-1-ref.html == flexbox-single-line-clamp-2.html flexbox-single-line-clamp-2-ref.html == flexbox-single-line-clamp-3.html flexbox-single-line-clamp-3-ref.html + +# Flexbox as an absolute containing block. +== position-absolute-containing-block-001.html position-absolute-containing-block-001-ref.html +== position-absolute-containing-block-002.html position-absolute-containing-block-002-ref.html -- cgit v1.2.3 From ca141778245946e9378704dbcf05355c6cb108f3 Mon Sep 17 00:00:00 2001 From: Lootyhoof Date: Fri, 15 Mar 2019 22:53:09 +0000 Subject: Draw a border when hiding the tab bar --- application/palemoon/themes/linux/browser.css | 11 +++++++++++ application/palemoon/themes/osx/browser.css | 11 +++++++++++ application/palemoon/themes/windows/browser.css | 24 +++++++++++++++++------- 3 files changed, 39 insertions(+), 7 deletions(-) diff --git a/application/palemoon/themes/linux/browser.css b/application/palemoon/themes/linux/browser.css index b545b06cb..933067c2b 100644 --- a/application/palemoon/themes/linux/browser.css +++ b/application/palemoon/themes/linux/browser.css @@ -1607,6 +1607,17 @@ richlistitem[type~="action"][actiontype="switchtab"] > .ac-url-box > .ac-action- background-image: linear-gradient(to top, rgba(0,0,0,.3) 1px, rgba(0,0,0,.05) 1px, transparent 50%); } +/* When the tab bar is collapsed, show a 1px border in its place. */ +#TabsToolbar[collapsed="true"] { + visibility: visible; + height: 1px; + border-bottom-width: 1px; + /* !important here to override border-style: none on the toolbar */ + border-bottom-style: solid !important; + border-bottom-color: ThreeDShadow; + overflow: hidden; +} + .tabbrowser-tab, .tabs-newtab-button { position: static; diff --git a/application/palemoon/themes/osx/browser.css b/application/palemoon/themes/osx/browser.css index ddf050785..20e8c5eac 100644 --- a/application/palemoon/themes/osx/browser.css +++ b/application/palemoon/themes/osx/browser.css @@ -1630,6 +1630,17 @@ richlistitem[type~="action"][actiontype="switchtab"][selected="true"] > .ac-url- background-image: linear-gradient(to top, @toolbarShadowColor@ 1px, rgba(0,0,0,.05) 1px, transparent 50%); } +/* When the tab bar is collapsed, show a 1px border in its place. */ +#TabsToolbar[collapsed="true"] { + visibility: visible; + height: 1px; + border-bottom-width: 1px; + /* !important here to override border-style: none on the toolbar */ + border-bottom-style: solid !important; + border-bottom-color: ThreeDShadow; + overflow: hidden; +} + @media (-moz-mac-lion-theme) { #main-window[sizemode=normal] #TabsToolbar { padding-left: 2px; diff --git a/application/palemoon/themes/windows/browser.css b/application/palemoon/themes/windows/browser.css index 56a8318da..8a47e67ce 100644 --- a/application/palemoon/themes/windows/browser.css +++ b/application/palemoon/themes/windows/browser.css @@ -31,6 +31,8 @@ %endif :root { + --toolbox-after-color: ThreeDShadow; + --toolbar-custom-color: hsl(210,75%,92%); --toolbar-highlight-top: rgba(255,255,255,.5); --toolbar-highlight-bottom: transparent; @@ -91,7 +93,7 @@ display: -moz-box; -moz-box-ordinal-group: 101; /* tabs toolbar is 100 */ height: 1px; - background-color: ThreeDShadow; + background-color: var(--toolbox-after-color); } #navigator-toolbox[tabsontop=false]::after, #main-window[disablechrome] #navigator-toolbox::after { @@ -1841,6 +1843,17 @@ richlistitem[type~="action"][actiontype="switchtab"] > .ac-url-box > .ac-action- background-image: linear-gradient(to top, @toolbarShadowColor@ 1px, rgba(0,0,0,.05) 1px, transparent 50%); } +/* When the tab bar is collapsed, show a 1px border in its place. */ +#TabsToolbar[collapsed="true"] { + visibility: visible; + height: 1px; + border-bottom-width: 1px; + /* !important here to override border-style: none on the toolbar */ + border-bottom-style: solid !important; + border-bottom-color: var(--toolbox-after-color); + overflow: hidden; +} + .tabbrowser-tab, .tabs-newtab-button { -moz-appearance: none; @@ -3044,20 +3057,17 @@ toolbar[brighttext] #addonbar-closebutton { @media (-moz-os-version: windows-vista), (-moz-os-version: windows-win7) { - #navigator-toolbox:not(:-moz-lwtheme)::after { - background-color: #aabccf; + :root { + --toolbox-after-color: #aabccf; } } @media (-moz-os-version: windows-win8), (-moz-os-version: windows-win10) { :root { + --toolbox-after-color: #bcbcbc; --toolbar-custom-color: hsl(210,0%,92%); } - - #navigator-toolbox:not(:-moz-lwtheme)::after { - background-color: #bcbcbc; - } } #navigator-toolbox[tabsontop=true] #urlbar:not(:-moz-lwtheme), -- cgit v1.2.3 From 07122c4454ef294067e77dcf1f04b1424dfe1f73 Mon Sep 17 00:00:00 2001 From: Lootyhoof Date: Fri, 15 Mar 2019 23:10:59 +0000 Subject: Don't modify toolbox-after-color in lwthemes --- application/palemoon/themes/windows/browser.css | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/application/palemoon/themes/windows/browser.css b/application/palemoon/themes/windows/browser.css index 8a47e67ce..aae36c539 100644 --- a/application/palemoon/themes/windows/browser.css +++ b/application/palemoon/themes/windows/browser.css @@ -3057,7 +3057,7 @@ toolbar[brighttext] #addonbar-closebutton { @media (-moz-os-version: windows-vista), (-moz-os-version: windows-win7) { - :root { + :root:not(:-moz-lwtheme) { --toolbox-after-color: #aabccf; } } @@ -3065,9 +3065,12 @@ toolbar[brighttext] #addonbar-closebutton { @media (-moz-os-version: windows-win8), (-moz-os-version: windows-win10) { :root { - --toolbox-after-color: #bcbcbc; --toolbar-custom-color: hsl(210,0%,92%); } + + :root:not(:-moz-lwtheme) { + --toolbox-after-color: #bcbcbc; + } } #navigator-toolbox[tabsontop=true] #urlbar:not(:-moz-lwtheme), -- cgit v1.2.3 From e9261d329b443e588de408ff85917ac29d4ab62d Mon Sep 17 00:00:00 2001 From: wolfbeast Date: Sat, 16 Mar 2019 13:54:20 +0100 Subject: Fix build bustage. --- dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp | 19 +++++++++++++++++-- dom/media/gmp/widevine-adapter/WidevineUtils.h | 4 ++++ 2 files changed, 21 insertions(+), 2 deletions(-) diff --git a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp index f89888a72..4d3408804 100644 --- a/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp +++ b/dom/media/gmp/widevine-adapter/WidevineDecryptor.cpp @@ -102,7 +102,7 @@ WidevineDecryptor::CreateSession(uint32_t aCreateSessionToken, } else { // Invalid init data type const char* errorMsg = "Invalid init data type when creating session."; - OnRejectPromise(aPromiseId, kNotSupportedError, 0, errorMsg, sizeof(errorMsg)); + OnRejectPromise(aPromiseId, kExceptionNotSupportedError, 0, errorMsg, sizeof(errorMsg)); return; } mPromiseIdToNewSessionTokens[aPromiseId] = aCreateSessionToken; @@ -338,6 +338,21 @@ WidevineDecryptor::OnResolvePromise(uint32_t aPromiseId) mCallback->ResolvePromise(aPromiseId); } +static GMPDOMException +ConvertCDMExceptionToGMPDOMException(cdm::Exception aException) +{ + switch (aException) { + case kExceptionNotSupportedError: return kGMPNotSupportedError; + case kExceptionInvalidStateError: return kGMPInvalidStateError; + case kExceptionTypeError: return kGMPTypeError; + case kExceptionQuotaExceededError: return kGMPQuotaExceededError; + case kUnknownError: return kGMPInvalidModificationError; // Note: Unique placeholder. + case kClientError: return kGMPAbortError; // Note: Unique placeholder. + case kOutputError: return kGMPSecurityError; // Note: Unique placeholder. + }; + return kGMPInvalidStateError; // Note: Unique placeholder. +} + // Align with spec, the Exceptions used by CDM to reject promises . // https://w3c.github.io/encrypted-media/#exceptions cdm::Exception @@ -376,7 +391,7 @@ WidevineDecryptor::OnRejectPromise(uint32_t aPromiseId, Log("Decryptor::OnRejectPromise(aPromiseId=%d, err=%d, sysCode=%u, msg=%s)", aPromiseId, (int)aException, aSystemCode, aErrorMessage); mCallback->RejectPromise(aPromiseId, - ToGMPDOMException(aException), + ConvertCDMExceptionToGMPDOMException(aException), !aErrorMessageSize ? "" : aErrorMessage, aErrorMessageSize); } diff --git a/dom/media/gmp/widevine-adapter/WidevineUtils.h b/dom/media/gmp/widevine-adapter/WidevineUtils.h index ca65ff881..2f6137fe3 100644 --- a/dom/media/gmp/widevine-adapter/WidevineUtils.h +++ b/dom/media/gmp/widevine-adapter/WidevineUtils.h @@ -51,6 +51,10 @@ public: explicit CDMWrapper(cdm::ContentDecryptionModule_9* aCDM, WidevineDecryptor* aDecryptor); cdm::ContentDecryptionModule_9* GetCDM() const { return mCDM; } + void OnStorageId(uint32_t aVersion, const uint8_t* aStorageId, + uint32_t aStorageIdSize) { + mCDM->OnStorageId(aVersion, aStorageId, aStorageIdSize); + } private: ~CDMWrapper(); cdm::ContentDecryptionModule_9* mCDM; -- cgit v1.2.3 From ad5bbbdb6b81b96248bf7a9197921356b6b15e0e Mon Sep 17 00:00:00 2001 From: Gaming4JC Date: Mon, 18 Mar 2019 18:26:48 -0400 Subject: Issue #756 - Remove Contextual Identity References from Pale Moon --- application/palemoon/app/profile/palemoon.js | 2 -- application/palemoon/base/content/browser.js | 4 ---- application/palemoon/base/content/content.js | 2 -- application/palemoon/base/content/tabbrowser.xml | 26 +++++++----------------- 4 files changed, 7 insertions(+), 27 deletions(-) diff --git a/application/palemoon/app/profile/palemoon.js b/application/palemoon/app/profile/palemoon.js index 85dc41c15..bd1b62cc3 100644 --- a/application/palemoon/app/profile/palemoon.js +++ b/application/palemoon/app/profile/palemoon.js @@ -1089,8 +1089,6 @@ pref("browser.pagethumbnails.capturing_disabled", false); // enables showing basic placeholders for missing thumbnails pref("browser.newtabpage.thumbnailPlaceholder", false); -pref("privacy.usercontext.about_newtab_segregation.enabled", false); - // number of columns of newtab grid pref("browser.newtabpage.columns", 4); diff --git a/application/palemoon/base/content/browser.js b/application/palemoon/base/content/browser.js index 4e753d422..b68f691a3 100644 --- a/application/palemoon/base/content/browser.js +++ b/application/palemoon/base/content/browser.js @@ -5338,9 +5338,6 @@ function handleDroppedLink(event, urlOrLinks, name) let lastLocationChange = gBrowser.selectedBrowser.lastLocationChange; - let userContextId = gBrowser.selectedBrowser - .getAttribute("usercontextid") || 0; - let inBackground = Services.prefs.getBoolPref("browser.tabs.loadInBackground"); if (event.shiftKey) inBackground = !inBackground; @@ -5359,7 +5356,6 @@ function handleDroppedLink(event, urlOrLinks, name) replace: true, allowThirdPartyFixup: false, postDatas, - userContextId, }); } }); diff --git a/application/palemoon/base/content/content.js b/application/palemoon/base/content/content.js index 653dac3e3..211a24a8b 100644 --- a/application/palemoon/base/content/content.js +++ b/application/palemoon/base/content/content.js @@ -139,7 +139,6 @@ var handleContentContextMenu = function (event) { let selectionInfo = BrowserUtils.getSelectionDetails(content); let loadContext = docShell.QueryInterface(Ci.nsILoadContext); - let userContextId = loadContext.originAttributes.userContextId; let browser = docShell.chromeEventHandler; let mainWin = browser.ownerGlobal; @@ -160,7 +159,6 @@ var handleContentContextMenu = function (event) { selectionInfo: selectionInfo, loginFillInfo, parentAllowsMixedContent, - userContextId, }; } diff --git a/application/palemoon/base/content/tabbrowser.xml b/application/palemoon/base/content/tabbrowser.xml index cbe029af0..868179b5d 100644 --- a/application/palemoon/base/content/tabbrowser.xml +++ b/application/palemoon/base/content/tabbrowser.xml @@ -737,8 +737,7 @@ let autocomplete = this.mTabBrowser._placesAutocomplete; if (this.mBrowser.registeredOpenURI) { - autocomplete.unregisterOpenPage(this.mBrowser.registeredOpenURI, - this.mBrowser.getAttribute("usercontextid") || 0); + autocomplete.unregisterOpenPage(this.mBrowser.registeredOpenURI); delete this.mBrowser.registeredOpenURI; } // Tabs in private windows aren't registered as "Open" so @@ -746,8 +745,7 @@ if (!isBlankPageURL(aLocation.spec) && (!PrivateBrowsingUtils.isWindowPrivate(window) || PrivateBrowsingUtils.permanentPrivateBrowsing)) { - autocomplete.registerOpenPage(aLocation, - this.mBrowser.getAttribute("usercontextid") || 0); + autocomplete.registerOpenPage(aLocation); this.mBrowser.registeredOpenURI = aLocation; } } @@ -1383,7 +1381,6 @@ let aTargetTab; let aNewIndex = -1; let aPostDatas = []; - let aUserContextId; if (arguments.length == 2 && typeof arguments[1] == "object") { let params = arguments[1]; @@ -1394,7 +1391,6 @@ aNewIndex = typeof params.newIndex === "number" ? params.newIndex : aNewIndex; aPostDatas = params.postDatas || aPostDatas; - aUserContextId = params.userContextId; } if (!aURIs.length) @@ -1443,8 +1439,7 @@ ownerTab: owner, skipAnimation: multiple, allowThirdPartyFixup: aAllowThirdPartyFixup, - postData: aPostDatas[0], - userContextId: aUserContextId + postData: aPostDatas[0] }); if (aNewIndex !== -1) { this.moveTabTo(firstTabAdded, aNewIndex); @@ -1457,8 +1452,7 @@ let tab = this.addTab(aURIs[i], { skipAnimation: true, allowThirdPartyFixup: aAllowThirdPartyFixup, - postData: aPostDatas[i], - userContextId: aUserContextId + postData: aPostDatas[i] }); if (targetTabIndex !== -1) this.moveTabTo(tab, ++tabNum); @@ -2059,8 +2053,7 @@ this.mTabListeners[aTab._tPos].destroy(); if (browser.registeredOpenURI && !aTabWillBeMoved) { - this._placesAutocomplete.unregisterOpenPage(browser.registeredOpenURI, - browser.getAttribute("usercontextid") || 0); + this._placesAutocomplete.unregisterOpenPage(browser.registeredOpenURI); delete browser.registeredOpenURI; } @@ -2428,8 +2421,7 @@ link.url); @@ -4810,7 +4799,6 @@ allowThirdPartyFixup: true, targetTab, newIndex, - userContextId, }); } -- cgit v1.2.3 From d0b4eb41bb6ac08171c164187bf33e03c58d4749 Mon Sep 17 00:00:00 2001 From: Gaming4JC Date: Mon, 18 Mar 2019 18:27:45 -0400 Subject: Issue #756 - Remove contextual identity from BackgroundPageThumbs.jsm reverts m-c 1279568, 1309699, 1310112 --- .../components/thumbnails/BackgroundPageThumbs.jsm | 40 +--------------------- 1 file changed, 1 insertion(+), 39 deletions(-) diff --git a/toolkit/components/thumbnails/BackgroundPageThumbs.jsm b/toolkit/components/thumbnails/BackgroundPageThumbs.jsm index 3ba0c346c..3ed32665d 100644 --- a/toolkit/components/thumbnails/BackgroundPageThumbs.jsm +++ b/toolkit/components/thumbnails/BackgroundPageThumbs.jsm @@ -15,8 +15,6 @@ const TELEMETRY_HISTOGRAM_ID_PREFIX = "FX_THUMBNAILS_BG_"; const XUL_NS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"; const HTML_NS = "http://www.w3.org/1999/xhtml"; -const ABOUT_NEWTAB_SEGREGATION_PREF = "privacy.usercontext.about_newtab_segregation.enabled"; - const { classes: Cc, interfaces: Ci, utils: Cu } = Components; Cu.import("resource://gre/modules/XPCOMUtils.jsm", this); @@ -37,8 +35,6 @@ XPCOMUtils.defineConstant(this, "TEL_CAPTURE_DONE_TIMEOUT", TEL_CAPTURE_DONE_TIM XPCOMUtils.defineConstant(this, "TEL_CAPTURE_DONE_CRASHED", TEL_CAPTURE_DONE_CRASHED); XPCOMUtils.defineConstant(this, "TEL_CAPTURE_DONE_BAD_URI", TEL_CAPTURE_DONE_BAD_URI); -XPCOMUtils.defineLazyModuleGetter(this, "ContextualIdentityService", - "resource://gre/modules/ContextualIdentityService.jsm"); const global = this; // contains base64 version of a placeholder thumbnail @@ -138,14 +134,6 @@ const BackgroundPageThumbs = { return url; }), - /** - * Tell the service that the thumbnail browser should be recreated at next - * call of _ensureBrowser(). - */ - renewThumbnailBrowser: function() { - this._renewThumbBrowser = true; - }, - /** * Ensures that initialization of the thumbnail browser's parent window has * begun. @@ -201,12 +189,9 @@ const BackgroundPageThumbs = { * Creates the thumbnail browser if it doesn't already exist. */ _ensureBrowser: function () { - if (this._thumbBrowser && !this._renewThumbBrowser) + if (this._thumbBrowser) return; - this._destroyBrowser(); - this._renewThumbBrowser = false; - let browser = this._parentWin.document.createElementNS(XUL_NS, "browser"); browser.setAttribute("type", "content"); browser.setAttribute("disableglobalhistory", "true"); @@ -216,13 +201,6 @@ const BackgroundPageThumbs = { browser.setAttribute("remote", "true"); } - if (Services.prefs.getBoolPref(ABOUT_NEWTAB_SEGREGATION_PREF)) { - // Use the private container for thumbnails. - let privateIdentity = - ContextualIdentityService.getPrivateIdentity("userContextIdInternal.thumbnail"); - browser.setAttribute("usercontextid", privateIdentity.userContextId); - } - // Size the browser. Make its aspect ratio the same as the canvases' that // the thumbnails are drawn into; the canvases' aspect ratio is the same as // the screen's, so use that. Aim for a size in the ballpark of 1024x768. @@ -325,14 +303,6 @@ const BackgroundPageThumbs = { _destroyBrowserTimeout: DESTROY_BROWSER_TIMEOUT, }; -Services.prefs.addObserver(ABOUT_NEWTAB_SEGREGATION_PREF, - function(aSubject, aTopic, aData) { - if (aTopic == "nsPref:changed" && aData == ABOUT_NEWTAB_SEGREGATION_PREF) { - BackgroundPageThumbs.renewThumbnailBrowser(); - } - }, - false); - Object.defineProperty(this, "BackgroundPageThumbs", { value: BackgroundPageThumbs, enumerable: true, @@ -467,14 +437,6 @@ Capture.prototype = { Cu.reportError(err); } } - - if (Services.prefs.getBoolPref(ABOUT_NEWTAB_SEGREGATION_PREF)) { - // Clear the data in the private container for thumbnails. - let privateIdentity = - ContextualIdentityService.getPrivateIdentity("userContextIdInternal.thumbnail"); - Services.obs.notifyObservers(null, "clear-origin-attributes-data", - JSON.stringify({ userContextId: privateIdentity.userContextId })); - } }; if (!data) { -- cgit v1.2.3 From 1f5194b5f1deb0f36b36ed886d94ce5f8b62ca9d Mon Sep 17 00:00:00 2001 From: Gaming4JC Date: Mon, 18 Mar 2019 20:51:28 -0400 Subject: Issue #756 - Remove Contextual Identity from Basilisk --- application/basilisk/app/profile/basilisk.js | 11 -- .../basilisk/base/content/browser-context.inc | 16 +- .../basilisk/base/content/browser-menubar.inc | 9 +- application/basilisk/base/content/browser.js | 125 +------------- application/basilisk/base/content/browser.xul | 8 +- application/basilisk/base/content/content.js | 6 +- application/basilisk/base/content/nsContextMenu.js | 34 +--- application/basilisk/base/content/tab-content.js | 27 --- application/basilisk/base/content/tabbrowser.xml | 187 ++------------------- .../basilisk/base/content/utilityOverlay.js | 81 +-------- .../contextualidentity/content/usercontext.css | 91 ---------- .../basilisk/components/contextualidentity/jar.mn | 6 - .../components/contextualidentity/moz.build | 7 - .../customizableui/CustomizableWidgets.jsm | 85 ---------- application/basilisk/components/moz.build | 1 - .../basilisk/components/preferences/containers.js | 176 ------------------- .../basilisk/components/preferences/containers.xul | 52 ------ .../basilisk/components/preferences/cookies.js | 39 +---- .../basilisk/components/preferences/cookies.xul | 4 - .../basilisk/components/preferences/handlers.css | 4 - .../basilisk/components/preferences/handlers.xml | 23 --- .../preferences/in-content/containers.js | 73 -------- .../preferences/in-content/containers.xul | 54 ------ .../components/preferences/in-content/jar.mn | 1 - .../preferences/in-content/preferences.js | 1 - .../preferences/in-content/preferences.xul | 11 -- .../components/preferences/in-content/privacy.js | 88 ---------- .../components/preferences/in-content/privacy.xul | 25 --- application/basilisk/components/preferences/jar.mn | 2 - .../components/sessionstore/ContentRestore.jsm | 4 - .../components/sessionstore/SessionHistory.jsm | 3 +- .../components/sessionstore/SessionStore.jsm | 42 ++--- .../basilisk/components/sessionstore/TabState.jsm | 4 - .../en-US/chrome/browser/browser.properties | 31 ---- .../chrome/browser/preferences/containers.dtd | 24 --- .../browser/preferences/containers.properties | 31 ---- .../en-US/chrome/browser/preferences/cookies.dtd | 1 - .../chrome/browser/preferences/preferences.dtd | 1 - .../browser/preferences/preferences.properties | 14 -- .../en-US/chrome/browser/preferences/privacy.dtd | 7 - application/basilisk/locales/jar.mn | 2 - application/basilisk/modules/ContentClick.jsm | 5 - .../themes/shared/incontentprefs/containers.css | 32 ---- .../shared/incontentprefs/preferences.inc.css | 3 +- application/basilisk/themes/shared/jar.inc.mn | 2 - .../themes/shared/preferences/containers.css | 53 ------ 46 files changed, 39 insertions(+), 1467 deletions(-) delete mode 100644 application/basilisk/components/contextualidentity/content/usercontext.css delete mode 100644 application/basilisk/components/contextualidentity/jar.mn delete mode 100644 application/basilisk/components/contextualidentity/moz.build delete mode 100644 application/basilisk/components/preferences/containers.js delete mode 100644 application/basilisk/components/preferences/containers.xul delete mode 100644 application/basilisk/components/preferences/in-content/containers.js delete mode 100644 application/basilisk/components/preferences/in-content/containers.xul delete mode 100644 application/basilisk/locales/en-US/chrome/browser/preferences/containers.dtd delete mode 100644 application/basilisk/locales/en-US/chrome/browser/preferences/containers.properties delete mode 100644 application/basilisk/themes/shared/incontentprefs/containers.css delete mode 100644 application/basilisk/themes/shared/preferences/containers.css diff --git a/application/basilisk/app/profile/basilisk.js b/application/basilisk/app/profile/basilisk.js index 24f1c582c..4700eac44 100644 --- a/application/basilisk/app/profile/basilisk.js +++ b/application/basilisk/app/profile/basilisk.js @@ -1293,17 +1293,6 @@ pref("privacy.trackingprotection.ui.enabled", true); pref("privacy.trackingprotection.ui.enabled", false); #endif -// Enable Contextual Identity Containers -#ifdef NIGHTLY_BUILD -pref("privacy.userContext.enabled", true); -pref("privacy.userContext.ui.enabled", true); -pref("privacy.usercontext.about_newtab_segregation.enabled", true); -#else -pref("privacy.userContext.enabled", false); -pref("privacy.userContext.ui.enabled", false); -pref("privacy.usercontext.about_newtab_segregation.enabled", false); -#endif - #ifndef RELEASE_OR_BETA // At the moment, autostart.2 is used, while autostart.1 is unused. // We leave it here set to false to reset users' defaults and allow diff --git a/application/basilisk/base/content/browser-context.inc b/application/basilisk/base/content/browser-context.inc index 36e0478af..2f6b19da0 100644 --- a/application/basilisk/base/content/browser-context.inc +++ b/application/basilisk/base/content/browser-context.inc @@ -51,23 +51,11 @@ label="&openLinkCmdInCurrent.label;" accesskey="&openLinkCmdInCurrent.accesskey;" oncommand="gContextMenu.openLinkInCurrent();"/> -# label and data-usercontextid are dynamically set. - +# label is dynamically set. - - + oncommand="gContextMenu.openLinkInTab();"/> - + - = 3) { let referrerURI = window.arguments[2]; if (typeof(referrerURI) == "string") { @@ -1179,13 +1148,11 @@ var gBrowserInit = { } let referrerPolicy = (window.arguments[5] != undefined ? window.arguments[5] : Ci.nsIHttpChannel.REFERRER_POLICY_DEFAULT); - let userContextId = (window.arguments[6] != undefined ? - window.arguments[6] : Ci.nsIScriptSecurityManager.DEFAULT_USER_CONTEXT_ID); loadURI(uriToLoad, referrerURI, window.arguments[3] || null, - window.arguments[4] || false, referrerPolicy, userContextId, + window.arguments[4] || false, referrerPolicy, // pass the origin principal (if any) and force its use to create // an initial about:blank viewer if present: - window.arguments[7], !!window.arguments[7], window.arguments[8]); + window.arguments[6], !!window.arguments[6], window.arguments[7]); window.focus(); } // Note: loadOneOrMoreURIs *must not* be called if window.arguments.length >= 3. @@ -2070,7 +2037,7 @@ function BrowserTryToCloseWindow() } function loadURI(uri, referrer, postData, allowThirdPartyFixup, referrerPolicy, - userContextId, originPrincipal, forceAboutBlankViewerInCurrent, + originPrincipal, forceAboutBlankViewerInCurrent, triggeringPrincipal) { try { openLinkIn(uri, "current", @@ -2078,7 +2045,6 @@ function loadURI(uri, referrer, postData, allowThirdPartyFixup, referrerPolicy, referrerPolicy: referrerPolicy, postData: postData, allowThirdPartyFixup: allowThirdPartyFixup, - userContextId: userContextId, originPrincipal, triggeringPrincipal, forceAboutBlankViewerInCurrent, @@ -3950,66 +3916,6 @@ function updateEditUIVisibility() } } -/** - * Opens a new tab with the userContextId specified as an attribute of - * sourceEvent. This attribute is propagated to the top level originAttributes - * living on the tab's docShell. - * - * @param event - * A click event on a userContext File Menu option - */ -function openNewUserContextTab(event) -{ - openUILinkIn(BROWSER_NEW_TAB_URL, "tab", { - userContextId: parseInt(event.target.getAttribute('data-usercontextid')), - }); -} - -/** - * Updates File Menu User Context UI visibility depending on - * privacy.userContext.enabled pref state. - */ -function updateUserContextUIVisibility() -{ - let menu = document.getElementById("menu_newUserContext"); - menu.hidden = !Services.prefs.getBoolPref("privacy.userContext.enabled"); - if (PrivateBrowsingUtils.isWindowPrivate(window)) { - menu.setAttribute("disabled", "true"); - } -} - -/** - * Updates the User Context UI indicators if the browser is in a non-default context - */ -function updateUserContextUIIndicator() -{ - let hbox = document.getElementById("userContext-icons"); - - let userContextId = gBrowser.selectedBrowser.getAttribute("usercontextid"); - if (!userContextId) { - hbox.setAttribute("data-identity-color", ""); - hbox.hidden = true; - return; - } - - let identity = ContextualIdentityService.getIdentityFromId(userContextId); - if (!identity) { - hbox.setAttribute("data-identity-color", ""); - hbox.hidden = true; - return; - } - - hbox.setAttribute("data-identity-color", identity.color); - - let label = document.getElementById("userContext-label"); - label.setAttribute("value", ContextualIdentityService.getUserContextLabel(userContextId)); - - let indicator = document.getElementById("userContext-indicator"); - indicator.setAttribute("data-identity-icon", identity.icon); - - hbox.hidden = false; -} - /** * Makes the Character Encoding menu enabled or disabled as appropriate. * To be called when the View menu or the app menu is opened. @@ -4690,7 +4596,6 @@ nsBrowserAccess.prototype = { _openURIInNewTab: function(aURI, aReferrer, aReferrerPolicy, aIsPrivate, aIsExternal, aForceNotRemote=false, - aUserContextId=Ci.nsIScriptSecurityManager.DEFAULT_USER_CONTEXT_ID, aOpener = null, aTriggeringPrincipal = null) { let win, needToFocusWin; @@ -4719,7 +4624,6 @@ nsBrowserAccess.prototype = { triggeringPrincipal: aTriggeringPrincipal, referrerURI: aReferrer, referrerPolicy: aReferrerPolicy, - userContextId: aUserContextId, fromExternal: aIsExternal, inBackground: loadInBackground, forceNotRemote: aForceNotRemote, @@ -4796,13 +4700,10 @@ nsBrowserAccess.prototype = { // will do the job of shuttling off the newly opened browser to run in // the right process once it starts loading a URI. let forceNotRemote = !!aOpener; - let userContextId = aOpener && aOpener.document - ? aOpener.document.nodePrincipal.originAttributes.userContextId - : Ci.nsIScriptSecurityManager.DEFAULT_USER_CONTEXT_ID; let openerWindow = (aFlags & Ci.nsIBrowserDOMWindow.OPEN_NO_OPENER) ? null : aOpener; let browser = this._openURIInNewTab(aURI, referrer, referrerPolicy, isPrivate, isExternal, - forceNotRemote, userContextId, + forceNotRemote, openerWindow, triggeringPrincipal); if (browser) newWindow = browser.contentWindow; @@ -4834,16 +4735,10 @@ nsBrowserAccess.prototype = { var isExternal = !!(aFlags & Ci.nsIBrowserDOMWindow.OPEN_EXTERNAL); - var userContextId = aParams.openerOriginAttributes && - ("userContextId" in aParams.openerOriginAttributes) - ? aParams.openerOriginAttributes.userContextId - : Ci.nsIScriptSecurityManager.DEFAULT_USER_CONTEXT_ID - let browser = this._openURIInNewTab(aURI, aParams.referrer, aParams.referrerPolicy, aParams.isPrivate, isExternal, false, - userContextId, null, aParams.triggeringPrincipal); if (browser) return browser.QueryInterface(Ci.nsIFrameLoaderOwner); @@ -5400,11 +5295,6 @@ function handleLinkClick(event, href, linkNode) { triggeringPrincipal: doc.nodePrincipal, }; - // The new tab/window must use the same userContextId - if (doc.nodePrincipal.originAttributes.userContextId) { - params.userContextId = doc.nodePrincipal.originAttributes.userContextId; - } - openLinkIn(href, where, params); event.preventDefault(); return true; @@ -5476,8 +5366,6 @@ function handleDroppedLink(event, urlOrLinks, name) let lastLocationChange = gBrowser.selectedBrowser.lastLocationChange; - let userContextId = gBrowser.selectedBrowser.getAttribute("usercontextid"); - // event is null if links are dropped in content process. // inBackground should be false, as it's loading into current browser. let inBackground = false; @@ -5501,7 +5389,6 @@ function handleDroppedLink(event, urlOrLinks, name) replace: true, allowThirdPartyFixup: false, postDatas, - userContextId, }); } }); diff --git a/application/basilisk/base/content/browser.xul b/application/basilisk/base/content/browser.xul index be64f1bac..0cc4c982a 100644 --- a/application/basilisk/base/content/browser.xul +++ b/application/basilisk/base/content/browser.xul @@ -8,7 +8,6 @@ - #ifdef MOZ_DEVTOOLS #endif @@ -551,12 +550,7 @@ key="key_undoCloseTab" label="&undoCloseTab.label;" observes="History:UndoCloseTab"/> - - - - - + diff --git a/application/basilisk/base/content/content.js b/application/basilisk/base/content/content.js index 5accbdf7b..d2a70ba11 100644 --- a/application/basilisk/base/content/content.js +++ b/application/basilisk/base/content/content.js @@ -162,9 +162,6 @@ var handleContentContextMenu = function (event) { let selectionInfo = BrowserUtils.getSelectionDetails(content); - let loadContext = docShell.QueryInterface(Ci.nsILoadContext); - let userContextId = loadContext.originAttributes.userContextId; - if (Services.appinfo.processType == Services.appinfo.PROCESS_TYPE_CONTENT) { let editFlags = SpellCheckHelper.isEditable(event.target, content); let spellInfo; @@ -188,7 +185,7 @@ var handleContentContextMenu = function (event) { principal, docLocation, charSet, baseURI, referrer, referrerPolicy, contentType, contentDisposition, frameOuterWindowID, selectionInfo, disableSetDesktopBg, - loginFillInfo, parentAllowsMixedContent, userContextId }, + loginFillInfo, parentAllowsMixedContent }, { event, popupNode: event.target }); } else { @@ -212,7 +209,6 @@ var handleContentContextMenu = function (event) { disableSetDesktopBackground: disableSetDesktopBg, loginFillInfo, parentAllowsMixedContent, - userContextId, }; } } diff --git a/application/basilisk/base/content/nsContextMenu.js b/application/basilisk/base/content/nsContextMenu.js index 3f77dcb90..74a2e7a8e 100644 --- a/application/basilisk/base/content/nsContextMenu.js +++ b/application/basilisk/base/content/nsContextMenu.js @@ -4,7 +4,6 @@ # License, v. 2.0. If a copy of the MPL was not distributed with this # file, You can obtain one at http://mozilla.org/MPL/2.0/. -Components.utils.import("resource://gre/modules/ContextualIdentityService.jsm"); Components.utils.import("resource://gre/modules/PrivateBrowsingUtils.jsm"); Components.utils.import("resource://gre/modules/InlineSpellChecker.jsm"); Components.utils.import("resource://gre/modules/LoginManagerContextMenu.jsm"); @@ -142,28 +141,11 @@ nsContextMenu.prototype = { this.onPlainTextLink = true; } - var inContainer = false; - if (gContextMenuContentData.userContextId) { - inContainer = true; - var item = document.getElementById("context-openlinkincontainertab"); - - item.setAttribute("data-usercontextid", gContextMenuContentData.userContextId); - - var label = - ContextualIdentityService.getUserContextLabel(gContextMenuContentData.userContextId); - item.setAttribute("label", - gBrowserBundle.formatStringFromName("userContextOpenLink.label", - [label], 1)); - } - var shouldShow = this.onSaveableLink || isMailtoInternal || this.onPlainTextLink; var isWindowPrivate = PrivateBrowsingUtils.isWindowPrivate(window); - var showContainers = Services.prefs.getBoolPref("privacy.userContext.enabled"); this.showItem("context-openlink", shouldShow && !isWindowPrivate); this.showItem("context-openlinkprivate", shouldShow); - this.showItem("context-openlinkintab", shouldShow && !inContainer); - this.showItem("context-openlinkincontainertab", shouldShow && inContainer); - this.showItem("context-openlinkinusercontext-menu", shouldShow && !isWindowPrivate && showContainers); + this.showItem("context-openlinkintab", shouldShow); this.showItem("context-openlinkincurrent", this.onPlainTextLink); this.showItem("context-sep-open", shouldShow); }, @@ -958,13 +940,6 @@ nsContextMenu.prototype = { params[p] = extra[p]; } - // If we want to change userContextId, we must be sure that we don't - // propagate the referrer. - if ("userContextId" in params && - params.userContextId != gContextMenuContentData.userContextId) { - params.noReferrer = true; - } - return params; }, @@ -982,7 +957,7 @@ nsContextMenu.prototype = { }, // Open linked-to URL in a new tab. - openLinkInTab: function(event) { + openLinkInTab: function() { urlSecurityCheck(this.linkURL, this.principal); let referrerURI = gContextMenuContentData.documentURIObject; @@ -1003,7 +978,6 @@ nsContextMenu.prototype = { let params = { allowMixedContent: persistAllowMixedContentInChildTab, - userContextId: parseInt(event.target.getAttribute('data-usercontextid')), }; openLinkIn(this.linkURL, "tab", this._openLinkInParameters(params)); @@ -1779,8 +1753,4 @@ nsContextMenu.prototype = { menuItem.label = menuLabel; menuItem.accessKey = gNavigatorBundle.getString("contextMenuSearch.accesskey"); }, - createContainerMenu: function(aEvent) { - return createUserContextMenu(aEvent, true, - gContextMenuContentData.userContextId); - }, }; diff --git a/application/basilisk/base/content/tab-content.js b/application/basilisk/base/content/tab-content.js index 7441b2140..35ef8ceb2 100644 --- a/application/basilisk/base/content/tab-content.js +++ b/application/basilisk/base/content/tab-content.js @@ -886,33 +886,6 @@ var RefreshBlocker = { RefreshBlocker.init(); -var UserContextIdNotifier = { - init() { - addEventListener("DOMWindowCreated", this); - }, - - uninit() { - removeEventListener("DOMWindowCreated", this); - }, - - handleEvent(aEvent) { - // When the window is created, we want to inform the tabbrowser about - // the userContextId in use in order to update the UI correctly. - // Just because we cannot change the userContextId from an active docShell, - // we don't need to check DOMContentLoaded again. - this.uninit(); - - // We use the docShell because content.document can have been loaded before - // setting the originAttributes. - let loadContext = docShell.QueryInterface(Ci.nsILoadContext); - let userContextId = loadContext.originAttributes.userContextId; - - sendAsyncMessage("Browser:WindowCreated", { userContextId }); - } -}; - -UserContextIdNotifier.init(); - addMessageListener("AllowScriptsToClose", () => { content.QueryInterface(Ci.nsIInterfaceRequestor) .getInterface(Ci.nsIDOMWindowUtils) diff --git a/application/basilisk/base/content/tabbrowser.xml b/application/basilisk/base/content/tabbrowser.xml index 52c51db69..c2f02512d 100644 --- a/application/basilisk/base/content/tabbrowser.xml +++ b/application/basilisk/base/content/tabbrowser.xml @@ -814,10 +814,8 @@ } let unifiedComplete = this.mTabBrowser._unifiedComplete; - let userContextId = this.mBrowser.getAttribute("usercontextid") || 0; if (this.mBrowser.registeredOpenURI) { - unifiedComplete.unregisterOpenPage(this.mBrowser.registeredOpenURI, - userContextId); + unifiedComplete.unregisterOpenPage(this.mBrowser.registeredOpenURI); delete this.mBrowser.registeredOpenURI; } // Tabs in private windows aren't registered as "Open" so @@ -825,7 +823,7 @@ if (!isBlankPageURL(aLocation.spec) && (!PrivateBrowsingUtils.isWindowPrivate(window) || PrivateBrowsingUtils.permanentPrivateBrowsing)) { - unifiedComplete.registerOpenPage(aLocation, userContextId); + unifiedComplete.registerOpenPage(aLocation); this.mBrowser.registeredOpenURI = aLocation; } } @@ -1230,7 +1228,6 @@ this._adjustFocusAfterTabSwitch(this.mCurrentTab); } - updateUserContextUIIndicator(); gIdentityHandler.updateSharingIndicator(); this.tabContainer._setPositionalAttributes(); @@ -1486,7 +1483,6 @@ var aSkipAnimation; var aForceNotRemote; var aNoReferrer; - var aUserContextId; var aRelatedBrowser; var aOriginPrincipal; var aOpener; @@ -1507,7 +1503,6 @@ aSkipAnimation = params.skipAnimation; aForceNotRemote = params.forceNotRemote; aNoReferrer = params.noReferrer; - aUserContextId = params.userContextId; aRelatedBrowser = params.relatedBrowser; aOriginPrincipal = params.originPrincipal; aOpener = params.opener; @@ -1530,7 +1525,6 @@ allowMixedContent: aAllowMixedContent, forceNotRemote: aForceNotRemote, noReferrer: aNoReferrer, - userContextId: aUserContextId, originPrincipal: aOriginPrincipal, relatedBrowser: aRelatedBrowser, opener: aOpener }); @@ -1551,7 +1545,6 @@ let aTargetTab; let aNewIndex = -1; let aPostDatas = []; - let aUserContextId; if (arguments.length == 2 && typeof arguments[1] == "object") { let params = arguments[1]; @@ -1562,7 +1555,6 @@ aNewIndex = typeof params.newIndex === "number" ? params.newIndex : aNewIndex; aPostDatas = params.postDatas || aPostDatas; - aUserContextId = params.userContextId; } if (!aURIs.length) @@ -1611,8 +1603,7 @@ ownerTab: owner, skipAnimation: multiple, allowThirdPartyFixup: aAllowThirdPartyFixup, - postData: aPostDatas[0], - userContextId: aUserContextId + postData: aPostDatas[0] }); if (aNewIndex !== -1) { this.moveTabTo(firstTabAdded, aNewIndex); @@ -1625,8 +1616,7 @@ let tab = this.addTab(aURIs[i], { skipAnimation: true, allowThirdPartyFixup: aAllowThirdPartyFixup, - postData: aPostDatas[i], - userContextId: aUserContextId + postData: aPostDatas[i] }); if (targetTabIndex !== -1) this.moveTabTo(tab, ++tabNum); @@ -1899,7 +1889,7 @@ - + - - - - document.getElementById(this.getAttribute("tabbrowser")); @@ -5302,55 +5242,6 @@ null null - - - - - - - let root = document.documentElement; @@ -6451,7 +6342,6 @@ inBackground = !inBackground; let targetTab = this._getDragTargetTab(event, true); - let userContextId = this.selectedItem.getAttribute("usercontextid"); let replace = !!targetTab; let newIndex = this._getDropIndex(event, true); let urls = links.map(link => link.url); @@ -6461,7 +6351,6 @@ allowThirdPartyFixup: true, targetTab, newIndex, - userContextId, }); } @@ -6722,14 +6611,6 @@ --> undefined - - - return this.hasAttribute("usercontextid") - ? parseInt(this.getAttribute("usercontextid")) - : 0; - - - return this.getAttribute("soundplaying") == "true"; @@ -6857,27 +6738,6 @@ ]]> - - - - - - - @@ -7054,30 +6914,9 @@ 0; i--) { @@ -7105,9 +6941,6 @@ menuItem.tab.mCorrespondingMenuitem = null; this.removeChild(menuItem); } - if (menuItem.hasAttribute("usercontextid")) { - this.removeChild(menuItem); - } } var tabcontainer = gBrowser.tabContainer; tabcontainer.mTabstrip.removeEventListener("scroll", this, false); diff --git a/application/basilisk/base/content/utilityOverlay.js b/application/basilisk/base/content/utilityOverlay.js index 38ca82f55..c8d85212f 100644 --- a/application/basilisk/base/content/utilityOverlay.js +++ b/application/basilisk/base/content/utilityOverlay.js @@ -5,7 +5,6 @@ // Services = object with smart getters for common XPCOM services Components.utils.import("resource://gre/modules/AppConstants.jsm"); -Components.utils.import("resource://gre/modules/ContextualIdentityService.jsm"); Components.utils.import("resource://gre/modules/Services.jsm"); Components.utils.import("resource://gre/modules/XPCOMUtils.jsm"); Components.utils.import("resource://gre/modules/PrivateBrowsingUtils.jsm"); @@ -176,7 +175,6 @@ function whereToOpenLink( e, ignoreButton, ignoreAlt ) * skipTabAnimation (boolean) * allowPinnedTabHostChange (boolean) * allowPopups (boolean) - * userContextId (unsigned int) */ function openUILinkIn(url, where, aAllowThirdPartyFixup, aPostData, aReferrerURI) { var params; @@ -222,7 +220,6 @@ function openLinkIn(url, where, params) { var aAllowPinnedTabHostChange = !!params.allowPinnedTabHostChange; var aNoReferrer = params.noReferrer; var aAllowPopups = !!params.allowPopups; - var aUserContextId = params.userContextId; var aIndicateErrorPageLoad = params.indicateErrorPageLoad; var aPrincipal = params.originPrincipal; var aTriggeringPrincipal = params.triggeringPrincipal; @@ -268,7 +265,6 @@ function openLinkIn(url, where, params) { function useOAForPrincipal(principal) { if (principal && principal.isCodebasePrincipal) { let attrs = { - userContextId: aUserContextId, privateBrowsingId: aIsPrivate || (w && PrivateBrowsingUtils.isWindowPrivate(w)), }; return Services.scriptSecurityManager.createCodebasePrincipal(principal.URI, attrs); @@ -315,17 +311,12 @@ function openLinkIn(url, where, params) { createInstance(Ci.nsISupportsPRUint32); referrerPolicySupports.data = aReferrerPolicy; - var userContextIdSupports = Cc["@mozilla.org/supports-PRUint32;1"]. - createInstance(Ci.nsISupportsPRUint32); - userContextIdSupports.data = aUserContextId; - sa.appendElement(wuri, /* weak =*/ false); sa.appendElement(charset, /* weak =*/ false); sa.appendElement(referrerURISupports, /* weak =*/ false); sa.appendElement(aPostData, /* weak =*/ false); sa.appendElement(allowThirdPartyFixupSupports, /* weak =*/ false); sa.appendElement(referrerPolicySupports, /* weak =*/ false); - sa.appendElement(userContextIdSupports, /* weak =*/ false); sa.appendElement(aPrincipal, /* weak =*/ false); sa.appendElement(aTriggeringPrincipal, /* weak =*/ false); @@ -418,8 +409,7 @@ function openLinkIn(url, where, params) { flags: flags, referrerURI: aNoReferrer ? null : aReferrerURI, referrerPolicy: aReferrerPolicy, - postData: aPostData, - userContextId: aUserContextId + postData: aPostData }); browserUsedForLoad = aCurrentBrowser; break; @@ -438,7 +428,6 @@ function openLinkIn(url, where, params) { skipAnimation: aSkipTabAnimation, allowMixedContent: aAllowMixedContent, noReferrer: aNoReferrer, - userContextId: aUserContextId, originPrincipal: aPrincipal, triggeringPrincipal: aTriggeringPrincipal, }); @@ -482,74 +471,6 @@ function checkForMiddleClick(node, event) { } } -// Populate a menu with user-context menu items. This method should be called -// by onpopupshowing passing the event as first argument. -function createUserContextMenu(event, isContextMenu = false, excludeUserContextId = 0) { - while (event.target.hasChildNodes()) { - event.target.removeChild(event.target.firstChild); - } - - let bundle = document.getElementById("bundle_browser"); - let docfrag = document.createDocumentFragment(); - - // If we are excluding a userContextId, we want to add a 'no-container' item. - if (excludeUserContextId) { - let menuitem = document.createElement("menuitem"); - menuitem.setAttribute("data-usercontextid", "0"); - menuitem.setAttribute("label", bundle.getString("userContextNone.label")); - menuitem.setAttribute("accesskey", bundle.getString("userContextNone.accesskey")); - - // We don't set an oncommand/command attribute because if we have - // to exclude a userContextId we are generating the contextMenu and - // isContextMenu will be true. - - docfrag.appendChild(menuitem); - - let menuseparator = document.createElement("menuseparator"); - docfrag.appendChild(menuseparator); - } - - ContextualIdentityService.getIdentities().forEach(identity => { - if (identity.userContextId == excludeUserContextId) { - return; - } - - let menuitem = document.createElement("menuitem"); - menuitem.setAttribute("data-usercontextid", identity.userContextId); - menuitem.setAttribute("label", ContextualIdentityService.getUserContextLabel(identity.userContextId)); - - if (identity.accessKey) { - menuitem.setAttribute("accesskey", bundle.getString(identity.accessKey)); - } - - menuitem.classList.add("menuitem-iconic"); - menuitem.setAttribute("data-identity-color", identity.color); - - if (!isContextMenu) { - menuitem.setAttribute("command", "Browser:NewUserContextTab"); - } - - menuitem.setAttribute("data-identity-icon", identity.icon); - - docfrag.appendChild(menuitem); - }); - - if (!isContextMenu) { - docfrag.appendChild(document.createElement("menuseparator")); - - let menuitem = document.createElement("menuitem"); - menuitem.setAttribute("label", - bundle.getString("userContext.aboutPage.label")); - menuitem.setAttribute("accesskey", - bundle.getString("userContext.aboutPage.accesskey")); - menuitem.setAttribute("command", "Browser:OpenAboutContainers"); - docfrag.appendChild(menuitem); - } - - event.target.appendChild(docfrag); - return true; -} - // Closes all popups that are ancestors of the node. function closeMenus(node) { diff --git a/application/basilisk/components/contextualidentity/content/usercontext.css b/application/basilisk/components/contextualidentity/content/usercontext.css deleted file mode 100644 index 728275d9f..000000000 --- a/application/basilisk/components/contextualidentity/content/usercontext.css +++ /dev/null @@ -1,91 +0,0 @@ -[data-identity-color="blue"] { - --identity-tab-color: #0996f8; - --identity-icon-color: #00a7e0; -} - -[data-identity-color="turquoise"] { - --identity-tab-color: #01bdad; - --identity-icon-color: #01bdad; -} - -[data-identity-color="green"] { - --identity-tab-color: #57bd35; - --identity-icon-color: #7dc14c; -} - -[data-identity-color="yellow"] { - --identity-tab-color: #ffcb00; - --identity-icon-color: #ffcb00; -} - -[data-identity-color="orange"] { - --identity-tab-color: #ff9216; - --identity-icon-color: #ff9216; -} - -[data-identity-color="red"] { - --identity-tab-color: #d92215; - --identity-icon-color: #d92215; -} - -[data-identity-color="pink"] { - --identity-tab-color: #ea385e; - --identity-icon-color: #ee5195; -} - -[data-identity-color="purple"] { - --identity-tab-color: #7a2f7a; - --identity-icon-color: #7a2f7a; -} - -[data-identity-icon="fingerprint"] { - --identity-icon: url("chrome://browser/content/usercontext.svg#fingerprint"); -} - -[data-identity-icon="briefcase"] { - --identity-icon: url("chrome://browser/content/usercontext.svg#briefcase"); -} - -[data-identity-icon="dollar"] { - --identity-icon: url("chrome://browser/content/usercontext.svg#dollar"); -} - -[data-identity-icon="cart"] { - --identity-icon: url("chrome://browser/content/usercontext.svg#cart"); -} - -[data-identity-icon="circle"] { - --identity-icon: url("chrome://browser/content/usercontext.svg#circle"); -} - -#userContext-indicator { - height: 16px; - width: 16px; -} - -#userContext-label { - margin-inline-end: 3px; - color: var(--identity-tab-color); -} - -#userContext-icons { - -moz-box-align: center; -} - -.tabbrowser-tab[usercontextid] { - background-image: linear-gradient(to right, transparent 20%, var(--identity-tab-color) 30%, var(--identity-tab-color) 70%, transparent 80%); - background-size: auto 2px; - background-repeat: no-repeat; -} - -.userContext-icon, -.menuitem-iconic[data-usercontextid] > .menu-iconic-left > .menu-iconic-icon, -.subviewbutton[usercontextid] > .toolbarbutton-icon, -#userContext-indicator { - background-image: var(--identity-icon); - filter: url(chrome://browser/skin/filters.svg#fill); - fill: var(--identity-icon-color); - background-size: contain; - background-repeat: no-repeat; - background-position: center center; -} diff --git a/application/basilisk/components/contextualidentity/jar.mn b/application/basilisk/components/contextualidentity/jar.mn deleted file mode 100644 index 848245949..000000000 --- a/application/basilisk/components/contextualidentity/jar.mn +++ /dev/null @@ -1,6 +0,0 @@ -# This Source Code Form is subject to the terms of the Mozilla Public -# License, v. 2.0. If a copy of the MPL was not distributed with this -# file, You can obtain one at http://mozilla.org/MPL/2.0/. - -browser.jar: - content/browser/usercontext/usercontext.css (content/usercontext.css) diff --git a/application/basilisk/components/contextualidentity/moz.build b/application/basilisk/components/contextualidentity/moz.build deleted file mode 100644 index aac3a838c..000000000 --- a/application/basilisk/components/contextualidentity/moz.build +++ /dev/null @@ -1,7 +0,0 @@ -# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*- -# vim: set filetype=python: -# This Source Code Form is subject to the terms of the Mozilla Public -# License, v. 2.0. If a copy of the MPL was not distributed with this -# file, You can obtain one at http://mozilla.org/MPL/2.0/. - -JAR_MANIFESTS += ['jar.mn'] diff --git a/application/basilisk/components/customizableui/CustomizableWidgets.jsm b/application/basilisk/components/customizableui/CustomizableWidgets.jsm index 09b3f167e..401b7ca74 100644 --- a/application/basilisk/components/customizableui/CustomizableWidgets.jsm +++ b/application/basilisk/components/customizableui/CustomizableWidgets.jsm @@ -23,8 +23,6 @@ XPCOMUtils.defineLazyModuleGetter(this, "CharsetMenu", "resource://gre/modules/CharsetMenu.jsm"); XPCOMUtils.defineLazyModuleGetter(this, "PrivateBrowsingUtils", "resource://gre/modules/PrivateBrowsingUtils.jsm"); -XPCOMUtils.defineLazyModuleGetter(this, "ContextualIdentityService", - "resource://gre/modules/ContextualIdentityService.jsm"); XPCOMUtils.defineLazyGetter(this, "CharsetBundle", function() { const kCharsetBundle = "chrome://global/locale/charsetMenu.properties"; @@ -977,89 +975,6 @@ const CustomizableWidgets = [ let win = aEvent.view; win.MailIntegration.sendLinkForBrowser(win.gBrowser.selectedBrowser) } - }, { - id: "containers-panelmenu", - type: "view", - viewId: "PanelUI-containers", - hasObserver: false, - onCreated: function(aNode) { - let doc = aNode.ownerDocument; - let win = doc.defaultView; - let items = doc.getElementById("PanelUI-containersItems"); - - let onItemCommand = function (aEvent) { - let item = aEvent.target; - if (item.hasAttribute("usercontextid")) { - let userContextId = parseInt(item.getAttribute("usercontextid")); - win.openUILinkIn(win.BROWSER_NEW_TAB_URL, "tab", {userContextId}); - } - }; - items.addEventListener("command", onItemCommand); - - if (PrivateBrowsingUtils.isWindowPrivate(win)) { - aNode.setAttribute("disabled", "true"); - } - - this.updateVisibility(aNode); - - if (!this.hasObserver) { - Services.prefs.addObserver("privacy.userContext.enabled", this, true); - this.hasObserver = true; - } - }, - onViewShowing: function(aEvent) { - let doc = aEvent.target.ownerDocument; - - let items = doc.getElementById("PanelUI-containersItems"); - - while (items.firstChild) { - items.firstChild.remove(); - } - - let fragment = doc.createDocumentFragment(); - let bundle = doc.getElementById("bundle_browser"); - - ContextualIdentityService.getIdentities().forEach(identity => { - let label = ContextualIdentityService.getUserContextLabel(identity.userContextId); - - let item = doc.createElementNS(kNSXUL, "toolbarbutton"); - item.setAttribute("label", label); - item.setAttribute("usercontextid", identity.userContextId); - item.setAttribute("class", "subviewbutton"); - item.setAttribute("data-identity-color", identity.color); - item.setAttribute("data-identity-icon", identity.icon); - - fragment.appendChild(item); - }); - - fragment.appendChild(doc.createElementNS(kNSXUL, "menuseparator")); - - let item = doc.createElementNS(kNSXUL, "toolbarbutton"); - item.setAttribute("label", bundle.getString("userContext.aboutPage.label")); - item.setAttribute("command", "Browser:OpenAboutContainers"); - item.setAttribute("class", "subviewbutton"); - fragment.appendChild(item); - - items.appendChild(fragment); - }, - - updateVisibility(aNode) { - aNode.hidden = !Services.prefs.getBoolPref("privacy.userContext.enabled"); - }, - - observe(aSubject, aTopic, aData) { - let {instances} = CustomizableUI.getWidget("containers-panelmenu"); - for (let {node} of instances) { - if (node) { - this.updateVisibility(node); - } - } - }, - - QueryInterface: XPCOMUtils.generateQI([ - Ci.nsISupportsWeakReference, - Ci.nsIObserver - ]), }]; let preferencesButton = { diff --git a/application/basilisk/components/moz.build b/application/basilisk/components/moz.build index a7685cbfc..65e8beb76 100644 --- a/application/basilisk/components/moz.build +++ b/application/basilisk/components/moz.build @@ -6,7 +6,6 @@ DIRS += [ 'about', - 'contextualidentity', 'customizableui', 'dirprovider', 'downloads', diff --git a/application/basilisk/components/preferences/containers.js b/application/basilisk/components/preferences/containers.js deleted file mode 100644 index 6ca5853f7..000000000 --- a/application/basilisk/components/preferences/containers.js +++ /dev/null @@ -1,176 +0,0 @@ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ - -Components.utils.import("resource://gre/modules/Services.jsm"); -Components.utils.import("resource://gre/modules/ContextualIdentityService.jsm"); - -const containersBundle = Services.strings.createBundle("chrome://browser/locale/preferences/containers.properties"); - -const HTMLNS = "http://www.w3.org/1999/xhtml"; - -let gContainersManager = { - icons: [ - "fingerprint", - "briefcase", - "dollar", - "cart", - "circle" - ], - - colors: [ - "blue", - "turquoise", - "green", - "yellow", - "orange", - "red", - "pink", - "purple" - ], - - onLoad() { - let params = window.arguments[0] || {}; - this.init(params); - }, - - init(aParams) { - this.userContextId = aParams.userContextId || null; - this.identity = aParams.identity; - - if (aParams.windowTitle) { - document.title = aParams.windowTitle; - } - - const iconWrapper = document.getElementById("iconWrapper"); - iconWrapper.appendChild(this.createIconButtons()); - - const colorWrapper = document.getElementById("colorWrapper"); - colorWrapper.appendChild(this.createColorSwatches()); - - if (this.identity.name) { - const name = document.getElementById("name"); - name.value = this.identity.name; - this.checkForm(); - } - - this.setLabelsMinWidth(); - - // This is to prevent layout jank caused by the svgs and outlines rendering at different times - document.getElementById("containers-content").removeAttribute("hidden"); - }, - - setLabelsMinWidth() { - const labelMinWidth = containersBundle.GetStringFromName("containers.labelMinWidth"); - const labels = [ - document.getElementById("nameLabel"), - document.getElementById("iconLabel"), - document.getElementById("colorLabel") - ]; - for (let label of labels) { - label.style.minWidth = labelMinWidth; - } - }, - - uninit() { - }, - - // Check if name string as to if the form can be submitted - checkForm() { - const name = document.getElementById("name"); - let btnApplyChanges = document.getElementById("btnApplyChanges"); - if (!name.value) { - btnApplyChanges.setAttribute("disabled", true); - } else { - btnApplyChanges.removeAttribute("disabled"); - } - }, - - createIconButtons(defaultIcon) { - let radiogroup = document.createElement("radiogroup"); - radiogroup.setAttribute("id", "icon"); - radiogroup.className = "icon-buttons"; - - for (let icon of this.icons) { - let iconSwatch = document.createElement("radio"); - iconSwatch.id = "iconbutton-" + icon; - iconSwatch.name = "icon"; - iconSwatch.type = "radio"; - iconSwatch.value = icon; - - if (this.identity.icon && this.identity.icon == icon) { - iconSwatch.setAttribute("selected", true); - } - - iconSwatch.setAttribute("label", - containersBundle.GetStringFromName(`containers.${icon}.label`)); - let iconElement = document.createElement("hbox"); - iconElement.className = 'userContext-icon'; - iconElement.setAttribute("data-identity-icon", icon); - - iconSwatch.appendChild(iconElement); - radiogroup.appendChild(iconSwatch); - } - - return radiogroup; - }, - - createColorSwatches(defaultColor) { - let radiogroup = document.createElement("radiogroup"); - radiogroup.setAttribute("id", "color"); - - for (let color of this.colors) { - let colorSwatch = document.createElement("radio"); - colorSwatch.id = "colorswatch-" + color; - colorSwatch.name = "color"; - colorSwatch.type = "radio"; - colorSwatch.value = color; - - if (this.identity.color && this.identity.color == color) { - colorSwatch.setAttribute("selected", true); - } - - colorSwatch.setAttribute("label", - containersBundle.GetStringFromName(`containers.${color}.label`)); - let iconElement = document.createElement("hbox"); - iconElement.className = 'userContext-icon'; - iconElement.setAttribute("data-identity-icon", "circle"); - iconElement.setAttribute("data-identity-color", color); - - colorSwatch.appendChild(iconElement); - radiogroup.appendChild(colorSwatch); - } - return radiogroup; - }, - - onApplyChanges() { - let icon = document.getElementById("icon").value; - let color = document.getElementById("color").value; - let name = document.getElementById("name").value; - - if (this.icons.indexOf(icon) == -1) { - throw "Internal error. The icon value doesn't match."; - } - - if (this.colors.indexOf(color) == -1) { - throw "Internal error. The color value doesn't match."; - } - - if (this.userContextId) { - ContextualIdentityService.update(this.userContextId, - name, - icon, - color); - } else { - ContextualIdentityService.create(name, - icon, - color); - } - window.parent.location.reload() - }, - - onWindowKeyPress(aEvent) { - if (aEvent.keyCode == KeyEvent.DOM_VK_ESCAPE) - window.close(); - } -} diff --git a/application/basilisk/components/preferences/containers.xul b/application/basilisk/components/preferences/containers.xul deleted file mode 100644 index 62a775fe4..000000000 --- a/application/basilisk/components/preferences/containers.xul +++ /dev/null @@ -1,52 +0,0 @@ - - - - - - - - - - - -