diff --git a/accessible/atk/AccessibleWrap.h b/accessible/atk/AccessibleWrap.h index 31401c4ef2f..57ca43439cf 100644 --- a/accessible/atk/AccessibleWrap.h +++ b/accessible/atk/AccessibleWrap.h @@ -52,11 +52,11 @@ public: virtual ~AccessibleWrap(); void ShutdownAtkObject(); - virtual void Shutdown(); + virtual void Shutdown() MOZ_OVERRIDE; // return the atk object for this AccessibleWrap virtual void GetNativeInterface(void** aOutAccessible) MOZ_OVERRIDE; - virtual nsresult HandleAccEvent(AccEvent* aEvent); + virtual nsresult HandleAccEvent(AccEvent* aEvent) MOZ_OVERRIDE; AtkObject * GetAtkObject(void); static AtkObject* GetAtkObject(Accessible* aAccessible); diff --git a/accessible/atk/ApplicationAccessibleWrap.h b/accessible/atk/ApplicationAccessibleWrap.h index f0480a3f2a8..c286e1f0ea9 100644 --- a/accessible/atk/ApplicationAccessibleWrap.h +++ b/accessible/atk/ApplicationAccessibleWrap.h @@ -19,9 +19,9 @@ public: virtual ~ApplicationAccessibleWrap(); // Accessible - virtual mozilla::a11y::ENameValueFlag Name(nsString& aName); + virtual mozilla::a11y::ENameValueFlag Name(nsString& aName) MOZ_OVERRIDE; virtual bool InsertChildAt(uint32_t aIdx, Accessible* aChild) MOZ_OVERRIDE; - virtual bool RemoveChild(Accessible* aChild); + virtual bool RemoveChild(Accessible* aChild) MOZ_OVERRIDE; /** * Return the atk object for app root accessible. diff --git a/accessible/atk/AtkSocketAccessible.h b/accessible/atk/AtkSocketAccessible.h index f807dc39c1d..476dcecb5d5 100644 --- a/accessible/atk/AtkSocketAccessible.h +++ b/accessible/atk/AtkSocketAccessible.h @@ -45,7 +45,7 @@ public: AtkSocketAccessible(nsIContent* aContent, DocAccessible* aDoc, const nsCString& aPlugId); - virtual void Shutdown(); + virtual void Shutdown() MOZ_OVERRIDE; virtual void GetNativeInterface(void** aOutAccessible) MOZ_OVERRIDE; }; diff --git a/accessible/base/AccCollector.h b/accessible/base/AccCollector.h index b62219761f7..f7c46f3adec 100644 --- a/accessible/base/AccCollector.h +++ b/accessible/base/AccCollector.h @@ -77,14 +77,14 @@ public: virtual ~EmbeddedObjCollector() { } public: - virtual int32_t GetIndexAt(Accessible* aAccessible); + virtual int32_t GetIndexAt(Accessible* aAccessible) MOZ_OVERRIDE; protected: // Make sure it's used by Accessible class only. explicit EmbeddedObjCollector(Accessible* aRoot) : AccCollector(aRoot, filters::GetEmbeddedObject) { } - virtual void AppendObject(Accessible* aAccessible); + virtual void AppendObject(Accessible* aAccessible) MOZ_OVERRIDE; friend class Accessible; }; diff --git a/accessible/base/AccEvent.h b/accessible/base/AccEvent.h index f96de77c240..29dc537a1c7 100644 --- a/accessible/base/AccEvent.h +++ b/accessible/base/AccEvent.h @@ -154,7 +154,7 @@ public: // AccEvent static const EventGroup kEventGroup = eStateChangeEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eStateChangeEvent); } @@ -183,7 +183,7 @@ public: // AccEvent static const EventGroup kEventGroup = eTextChangeEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eTextChangeEvent); } @@ -223,7 +223,7 @@ public: // Event static const EventGroup kEventGroup = eMutationEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eMutationEvent); } @@ -253,7 +253,7 @@ public: // Event static const EventGroup kEventGroup = eHideEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccMutationEvent::GetEventGroups() | (1U << eHideEvent); } @@ -281,7 +281,7 @@ public: // Event static const EventGroup kEventGroup = eShowEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccMutationEvent::GetEventGroups() | (1U << eShowEvent); } @@ -301,7 +301,7 @@ public: // Event static const EventGroup kEventGroup = eReorderEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eReorderEvent); } @@ -354,7 +354,7 @@ public: // AccEvent static const EventGroup kEventGroup = eCaretMoveEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eCaretMoveEvent); } @@ -380,7 +380,7 @@ public: // AccEvent static const EventGroup kEventGroup = eTextSelChangeEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eTextSelChangeEvent); } @@ -419,7 +419,7 @@ public: // AccEvent static const EventGroup kEventGroup = eSelectionChangeEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eSelectionChangeEvent); } @@ -449,7 +449,7 @@ public: // AccEvent static const EventGroup kEventGroup = eTableChangeEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eTableChangeEvent); } @@ -479,7 +479,7 @@ public: // AccEvent static const EventGroup kEventGroup = eVirtualCursorChangeEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eVirtualCursorChangeEvent); } @@ -509,7 +509,7 @@ public: // AccEvent static const EventGroup kEventGroup = eObjectAttrChangedEvent; - virtual unsigned int GetEventGroups() const + virtual unsigned int GetEventGroups() const MOZ_OVERRIDE { return AccEvent::GetEventGroups() | (1U << eObjectAttrChangedEvent); } diff --git a/accessible/base/AccIterator.h b/accessible/base/AccIterator.h index 5f96135fc6e..503c8c39314 100644 --- a/accessible/base/AccIterator.h +++ b/accessible/base/AccIterator.h @@ -43,7 +43,7 @@ public: * Return next accessible complying with filter function. Return the first * accessible for the first time. */ - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: AccIterator(); @@ -89,7 +89,7 @@ public: /** * Return next related accessible for the given dependent accessible. */ - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: RelatedAccIterator(); @@ -123,7 +123,7 @@ public: /** * Return next label accessible associated with the given element. */ - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: HTMLLabelIterator(); @@ -150,7 +150,7 @@ public: /** * Return next output accessible associated with the given element. */ - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: HTMLOutputIterator(); @@ -173,7 +173,7 @@ public: /** * Return next label accessible associated with the given element. */ - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: XULLabelIterator(); @@ -196,7 +196,7 @@ public: /** * Return next description accessible associated with the given element. */ - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: XULDescriptionIterator(); @@ -234,7 +234,7 @@ public: nsIContent* GetElem(const nsDependentSubstring& aID); // AccIterable - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: IDRefsIterator(); @@ -257,7 +257,7 @@ public: explicit SingleAccIterator(Accessible* aTarget): mAcc(aTarget) { } virtual ~SingleAccIterator() { } - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: SingleAccIterator(); @@ -278,7 +278,7 @@ public: mContainer(aItemContainer), mAnchor(nullptr) { } virtual ~ItemIterator() { } - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: ItemIterator() = delete; @@ -300,7 +300,7 @@ public: int32_t aRowIdx); virtual ~XULTreeItemIterator() { } - virtual Accessible* Next(); + virtual Accessible* Next() MOZ_OVERRIDE; private: XULTreeItemIterator() = delete; diff --git a/accessible/base/NotificationController.h b/accessible/base/NotificationController.h index 90b6dcb7b02..de8dba3cd46 100644 --- a/accessible/base/NotificationController.h +++ b/accessible/base/NotificationController.h @@ -64,7 +64,7 @@ public: mInstance(aInstance), mCallback(aCallback), mArg(aArg) { } virtual ~TNotification() { mInstance = nullptr; } - virtual void Process() + virtual void Process() MOZ_OVERRIDE { (mInstance->*mCallback)(mArg); @@ -91,8 +91,8 @@ class NotificationController MOZ_FINAL : public EventQueue, public: NotificationController(DocAccessible* aDocument, nsIPresShell* aPresShell); - NS_IMETHOD_(MozExternalRefCountType) AddRef(void); - NS_IMETHOD_(MozExternalRefCountType) Release(void); + NS_IMETHOD_(MozExternalRefCountType) AddRef(void) MOZ_OVERRIDE; + NS_IMETHOD_(MozExternalRefCountType) Release(void) MOZ_OVERRIDE; NS_DECL_CYCLE_COLLECTION_NATIVE_CLASS(NotificationController) @@ -203,7 +203,7 @@ private: NotificationController& operator = (const NotificationController&); // nsARefreshObserver - virtual void WillRefresh(mozilla::TimeStamp aTime); + virtual void WillRefresh(mozilla::TimeStamp aTime) MOZ_OVERRIDE; private: /** diff --git a/accessible/base/TextAttrs.h b/accessible/base/TextAttrs.h index 1c5d54c25fa..7f6967e40c2 100644 --- a/accessible/base/TextAttrs.h +++ b/accessible/base/TextAttrs.h @@ -130,7 +130,7 @@ protected: // TextAttr virtual void Expose(nsIPersistentProperties* aAttributes, - bool aIncludeDefAttrValue) + bool aIncludeDefAttrValue) MOZ_OVERRIDE { if (mGetRootValue) { if (mIsRootDefined) @@ -148,7 +148,7 @@ protected: ExposeValue(aAttributes, mRootNativeValue); } - virtual bool Equal(Accessible* aAccessible) + virtual bool Equal(Accessible* aAccessible) MOZ_OVERRIDE { T nativeValue; bool isDefined = GetValueFor(aAccessible, &nativeValue); @@ -203,9 +203,9 @@ protected: protected: // TextAttr - virtual bool GetValueFor(Accessible* aAccessible, nsString* aValue); + virtual bool GetValueFor(Accessible* aAccessible, nsString* aValue) MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const nsString& aValue); + const nsString& aValue) MOZ_OVERRIDE; private: nsCOMPtr mRootContent; @@ -234,9 +234,9 @@ protected: }; // TextAttr - virtual bool GetValueFor(Accessible* aAccessible, uint32_t* aValue); + virtual bool GetValueFor(Accessible* aAccessible, uint32_t* aValue) MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const uint32_t& aValue); + const uint32_t& aValue) MOZ_OVERRIDE; private: bool GetValue(nsIContent* aElm, uint32_t* aValue); @@ -256,9 +256,10 @@ protected: protected: // TextAttr - virtual bool GetValueFor(Accessible* aAccessible, nscolor* aValue); + virtual bool GetValueFor(Accessible* aAccessible, nscolor* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const nscolor& aValue); + const nscolor& aValue) MOZ_OVERRIDE; private: bool GetColor(nsIFrame* aFrame, nscolor* aColor); @@ -278,9 +279,10 @@ protected: protected: // TTextAttr - virtual bool GetValueFor(Accessible* aAccessible, nscolor* aValue); + virtual bool GetValueFor(Accessible* aAccessible, nscolor* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const nscolor& aValue); + const nscolor& aValue) MOZ_OVERRIDE; }; @@ -296,9 +298,10 @@ protected: protected: // TTextAttr - virtual bool GetValueFor(Accessible* aAccessible, nsString* aValue); + virtual bool GetValueFor(Accessible* aAccessible, nsString* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const nsString& aValue); + const nsString& aValue) MOZ_OVERRIDE; private: @@ -318,9 +321,10 @@ protected: protected: // TTextAttr - virtual bool GetValueFor(Accessible* aAccessible, nscoord* aValue); + virtual bool GetValueFor(Accessible* aAccessible, nscoord* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const nscoord& aValue); + const nscoord& aValue) MOZ_OVERRIDE; private: nsDeviceContext* mDC; @@ -339,9 +343,10 @@ protected: protected: // TTextAttr - virtual bool GetValueFor(Accessible* aContent, nscoord* aValue); + virtual bool GetValueFor(Accessible* aContent, nscoord* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const nscoord& aValue); + const nscoord& aValue) MOZ_OVERRIDE; }; @@ -357,9 +362,10 @@ protected: protected: // TTextAttr - virtual bool GetValueFor(Accessible* aAccessible, int32_t* aValue); + virtual bool GetValueFor(Accessible* aAccessible, int32_t* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const int32_t& aValue); + const int32_t& aValue) MOZ_OVERRIDE; private: int32_t GetFontWeight(nsIFrame* aFrame); @@ -377,9 +383,10 @@ protected: protected: // TextAttr - virtual bool GetValueFor(Accessible* aAccessible, bool* aValue); + virtual bool GetValueFor(Accessible* aAccessible, bool* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const bool& aValue); + const bool& aValue) MOZ_OVERRIDE; }; @@ -428,9 +435,10 @@ protected: protected: // TextAttr - virtual bool GetValueFor(Accessible* aAccessible, TextDecorValue* aValue); + virtual bool GetValueFor(Accessible* aAccessible, TextDecorValue* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const TextDecorValue& aValue); + const TextDecorValue& aValue) MOZ_OVERRIDE; }; /** @@ -453,9 +461,10 @@ protected: protected: // TextAttr - virtual bool GetValueFor(Accessible* aAccessible, TextPosValue* aValue); + virtual bool GetValueFor(Accessible* aAccessible, TextPosValue* aValue) + MOZ_OVERRIDE; virtual void ExposeValue(nsIPersistentProperties* aAttributes, - const TextPosValue& aValue); + const TextPosValue& aValue) MOZ_OVERRIDE; private: TextPosValue GetTextPosValue(nsIFrame* aFrame) const; diff --git a/accessible/generic/Accessible.cpp b/accessible/generic/Accessible.cpp index 8ee79e62995..c5ff7991618 100644 --- a/accessible/generic/Accessible.cpp +++ b/accessible/generic/Accessible.cpp @@ -1729,7 +1729,7 @@ Accessible::DoCommand(nsIContent *aContent, uint32_t aActionIndex) Runnable(Accessible* aAcc, nsIContent* aContent, uint32_t aIdx) : mAcc(aAcc), mContent(aContent), mIdx(aIdx) { } - NS_IMETHOD Run() + NS_IMETHOD Run() MOZ_OVERRIDE { if (mAcc) mAcc->DispatchClickEvent(mContent, mIdx); diff --git a/accessible/xpcom/xpcAccessible.h b/accessible/xpcom/xpcAccessible.h index 85e45fd6b55..f179bb058ec 100644 --- a/accessible/xpcom/xpcAccessible.h +++ b/accessible/xpcom/xpcAccessible.h @@ -24,60 +24,68 @@ class xpcAccessible : public nsIAccessible { public: // nsIAccessible - NS_IMETHOD GetParent(nsIAccessible** aParent) MOZ_FINAL; - NS_IMETHOD GetNextSibling(nsIAccessible** aNextSibling) MOZ_FINAL; - NS_IMETHOD GetPreviousSibling(nsIAccessible** aPreviousSibling) MOZ_FINAL; - NS_IMETHOD GetFirstChild(nsIAccessible** aFirstChild) MOZ_FINAL; - NS_IMETHOD GetLastChild(nsIAccessible** aLastChild) MOZ_FINAL; - NS_IMETHOD GetChildCount(int32_t* aChildCount) MOZ_FINAL; - NS_IMETHOD GetChildAt(int32_t aChildIndex, nsIAccessible** aChild) MOZ_FINAL; - NS_IMETHOD GetChildren(nsIArray** aChildren) MOZ_FINAL; - NS_IMETHOD GetIndexInParent(int32_t* aIndexInParent) MOZ_FINAL; + NS_IMETHOD GetParent(nsIAccessible** aParent) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetNextSibling(nsIAccessible** aNextSibling) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetPreviousSibling(nsIAccessible** aPreviousSibling) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetFirstChild(nsIAccessible** aFirstChild) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetLastChild(nsIAccessible** aLastChild) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetChildCount(int32_t* aChildCount) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetChildAt(int32_t aChildIndex, nsIAccessible** aChild) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetChildren(nsIArray** aChildren) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetIndexInParent(int32_t* aIndexInParent) MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetDOMNode(nsIDOMNode** aDOMNode) MOZ_FINAL; - NS_IMETHOD GetDocument(nsIAccessibleDocument** aDocument) MOZ_FINAL; - NS_IMETHOD GetRootDocument(nsIAccessibleDocument** aRootDocument) MOZ_FINAL; + NS_IMETHOD GetDOMNode(nsIDOMNode** aDOMNode) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetDocument(nsIAccessibleDocument** aDocument) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRootDocument(nsIAccessibleDocument** aRootDocument) + MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetRole(uint32_t* aRole) MOZ_FINAL; - NS_IMETHOD GetState(uint32_t* aState, uint32_t* aExtraState) MOZ_FINAL; + NS_IMETHOD GetRole(uint32_t* aRole) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetState(uint32_t* aState, uint32_t* aExtraState) + MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetDescription(nsAString& aDescription) MOZ_FINAL; - NS_IMETHOD GetName(nsAString& aName) MOZ_FINAL; - NS_IMETHOD GetLanguage(nsAString& aLanguage) MOZ_FINAL; - NS_IMETHOD GetValue(nsAString& aValue) MOZ_FINAL; - NS_IMETHOD GetHelp(nsAString& aHelp) MOZ_FINAL; + NS_IMETHOD GetDescription(nsAString& aDescription) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetName(nsAString& aName) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetLanguage(nsAString& aLanguage) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetValue(nsAString& aValue) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetHelp(nsAString& aHelp) MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetAccessKey(nsAString& aAccessKey) MOZ_FINAL; - NS_IMETHOD GetKeyboardShortcut(nsAString& aKeyBinding) MOZ_FINAL; + NS_IMETHOD GetAccessKey(nsAString& aAccessKey) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetKeyboardShortcut(nsAString& aKeyBinding) MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetAttributes(nsIPersistentProperties** aAttributes) MOZ_FINAL; + NS_IMETHOD GetAttributes(nsIPersistentProperties** aAttributes) + MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetBounds(int32_t* aX, int32_t* aY, - int32_t* aWidth, int32_t* aHeight) MOZ_FINAL; + int32_t* aWidth, int32_t* aHeight) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GroupPosition(int32_t* aGroupLevel, int32_t* aSimilarItemsInGroup, - int32_t* aPositionInGroup) MOZ_FINAL; + int32_t* aPositionInGroup) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetRelationByType(uint32_t aType, - nsIAccessibleRelation** aRelation) MOZ_FINAL; - NS_IMETHOD GetRelations(nsIArray** aRelations) MOZ_FINAL; + nsIAccessibleRelation** aRelation) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRelations(nsIArray** aRelations) MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetFocusedChild(nsIAccessible** aChild) MOZ_FINAL; + NS_IMETHOD GetFocusedChild(nsIAccessible** aChild) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetChildAtPoint(int32_t aX, int32_t aY, - nsIAccessible** aAccessible) MOZ_FINAL; + nsIAccessible** aAccessible) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetDeepestChildAtPoint(int32_t aX, int32_t aY, - nsIAccessible** aAccessible) MOZ_FINAL; + nsIAccessible** aAccessible) + MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD SetSelected(bool aSelect) MOZ_FINAL; - NS_IMETHOD ExtendSelection() MOZ_FINAL; - NS_IMETHOD TakeSelection() MOZ_FINAL; - NS_IMETHOD TakeFocus() MOZ_FINAL; + NS_IMETHOD SetSelected(bool aSelect) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD ExtendSelection() MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD TakeSelection() MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD TakeFocus() MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD GetActionCount(uint8_t* aActionCount) MOZ_FINAL; - NS_IMETHOD GetActionName(uint8_t aIndex, nsAString& aName) MOZ_FINAL; - NS_IMETHOD GetActionDescription(uint8_t aIndex, nsAString& aDescription) MOZ_FINAL; - NS_IMETHOD DoAction(uint8_t aIndex) MOZ_FINAL; + NS_IMETHOD GetActionCount(uint8_t* aActionCount) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetActionName(uint8_t aIndex, nsAString& aName) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetActionDescription(uint8_t aIndex, nsAString& aDescription) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD DoAction(uint8_t aIndex) MOZ_FINAL MOZ_OVERRIDE; - NS_IMETHOD ScrollTo(uint32_t aHow) MOZ_FINAL; + NS_IMETHOD ScrollTo(uint32_t aHow) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD ScrollToPoint(uint32_t aCoordinateType, - int32_t aX, int32_t aY) MOZ_FINAL; + int32_t aX, int32_t aY) MOZ_FINAL MOZ_OVERRIDE; protected: xpcAccessible() { } diff --git a/accessible/xpcom/xpcAccessibleApplication.h b/accessible/xpcom/xpcAccessibleApplication.h index e5c849c33b0..a0c9ea458ee 100644 --- a/accessible/xpcom/xpcAccessibleApplication.h +++ b/accessible/xpcom/xpcAccessibleApplication.h @@ -27,10 +27,10 @@ public: NS_DECL_ISUPPORTS_INHERITED // nsIAccessibleApplication - NS_IMETHOD GetAppName(nsAString& aName) MOZ_FINAL; - NS_IMETHOD GetAppVersion(nsAString& aVersion) MOZ_FINAL; - NS_IMETHOD GetPlatformName(nsAString& aName) MOZ_FINAL; - NS_IMETHOD GetPlatformVersion(nsAString& aVersion) MOZ_FINAL; + NS_IMETHOD GetAppName(nsAString& aName) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetAppVersion(nsAString& aVersion) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetPlatformName(nsAString& aName) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetPlatformVersion(nsAString& aVersion) MOZ_FINAL MOZ_OVERRIDE; protected: virtual ~xpcAccessibleApplication() {} diff --git a/accessible/xpcom/xpcAccessibleDocument.h b/accessible/xpcom/xpcAccessibleDocument.h index 59a33ad2e95..04f973b9b94 100644 --- a/accessible/xpcom/xpcAccessibleDocument.h +++ b/accessible/xpcom/xpcAccessibleDocument.h @@ -32,17 +32,20 @@ public: xpcAccessibleGeneric) // nsIAccessibleDocument - NS_IMETHOD GetURL(nsAString& aURL) MOZ_FINAL; - NS_IMETHOD GetTitle(nsAString& aTitle) MOZ_FINAL; - NS_IMETHOD GetMimeType(nsAString& aType) MOZ_FINAL; - NS_IMETHOD GetDocType(nsAString& aType) MOZ_FINAL; - NS_IMETHOD GetDOMDocument(nsIDOMDocument** aDOMDocument) MOZ_FINAL; - NS_IMETHOD GetWindow(nsIDOMWindow** aDOMWindow) MOZ_FINAL; - NS_IMETHOD GetParentDocument(nsIAccessibleDocument** aDocument) MOZ_FINAL; - NS_IMETHOD GetChildDocumentCount(uint32_t* aCount) MOZ_FINAL; + NS_IMETHOD GetURL(nsAString& aURL) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetTitle(nsAString& aTitle) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetMimeType(nsAString& aType) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetDocType(nsAString& aType) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetDOMDocument(nsIDOMDocument** aDOMDocument) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetWindow(nsIDOMWindow** aDOMWindow) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetParentDocument(nsIAccessibleDocument** aDocument) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetChildDocumentCount(uint32_t* aCount) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetChildDocumentAt(uint32_t aIndex, - nsIAccessibleDocument** aDocument) MOZ_FINAL; - NS_IMETHOD GetVirtualCursor(nsIAccessiblePivot** aVirtualCursor) MOZ_FINAL; + nsIAccessibleDocument** aDocument) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetVirtualCursor(nsIAccessiblePivot** aVirtualCursor) + MOZ_FINAL MOZ_OVERRIDE; /** * Return XPCOM wrapper for the internal accessible. diff --git a/accessible/xpcom/xpcAccessibleGeneric.h b/accessible/xpcom/xpcAccessibleGeneric.h index fff77c2be4d..dc466a13b6f 100644 --- a/accessible/xpcom/xpcAccessibleGeneric.h +++ b/accessible/xpcom/xpcAccessibleGeneric.h @@ -41,7 +41,7 @@ public: NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(xpcAccessibleGeneric, nsIAccessible) // nsIAccessible - virtual Accessible* ToInternalAccessible() const MOZ_FINAL; + virtual Accessible* ToInternalAccessible() const MOZ_FINAL MOZ_OVERRIDE; // xpcAccessibleGeneric virtual void Shutdown(); diff --git a/accessible/xpcom/xpcAccessibleHyperLink.h b/accessible/xpcom/xpcAccessibleHyperLink.h index 54820863048..0d71eb214f5 100644 --- a/accessible/xpcom/xpcAccessibleHyperLink.h +++ b/accessible/xpcom/xpcAccessibleHyperLink.h @@ -23,12 +23,13 @@ class Accessible; class xpcAccessibleHyperLink : public nsIAccessibleHyperLink { public: - NS_IMETHOD GetAnchorCount(int32_t* aAnchorCount) MOZ_FINAL; - NS_IMETHOD GetStartIndex(int32_t* aStartIndex) MOZ_FINAL; - NS_IMETHOD GetEndIndex(int32_t* aEndIndex) MOZ_FINAL; - NS_IMETHOD GetURI(int32_t aIndex, nsIURI** aURI) MOZ_FINAL; - NS_IMETHOD GetAnchor(int32_t aIndex, nsIAccessible** aAccessible) MOZ_FINAL; - NS_IMETHOD GetValid(bool* aValid) MOZ_FINAL; + NS_IMETHOD GetAnchorCount(int32_t* aAnchorCount) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetStartIndex(int32_t* aStartIndex) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetEndIndex(int32_t* aEndIndex) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetURI(int32_t aIndex, nsIURI** aURI) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetAnchor(int32_t aIndex, nsIAccessible** aAccessible) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetValid(bool* aValid) MOZ_FINAL MOZ_OVERRIDE; protected: xpcAccessibleHyperLink() { } diff --git a/accessible/xpcom/xpcAccessibleImage.h b/accessible/xpcom/xpcAccessibleImage.h index 19171898a27..6ed751b6691 100644 --- a/accessible/xpcom/xpcAccessibleImage.h +++ b/accessible/xpcom/xpcAccessibleImage.h @@ -24,8 +24,8 @@ public: NS_DECL_ISUPPORTS_INHERITED NS_IMETHOD GetImagePosition(uint32_t aCoordType, - int32_t* aX, int32_t* aY) MOZ_FINAL; - NS_IMETHOD GetImageSize(int32_t* aWidth, int32_t* aHeight) MOZ_FINAL; + int32_t* aX, int32_t* aY) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetImageSize(int32_t* aWidth, int32_t* aHeight) MOZ_FINAL MOZ_OVERRIDE; protected: virtual ~xpcAccessibleImage() {} diff --git a/accessible/xpcom/xpcAccessibleSelectable.h b/accessible/xpcom/xpcAccessibleSelectable.h index 1039ca28a1b..a87bb4c146d 100644 --- a/accessible/xpcom/xpcAccessibleSelectable.h +++ b/accessible/xpcom/xpcAccessibleSelectable.h @@ -25,14 +25,17 @@ class xpcAccessibleSelectable : public nsIAccessibleSelectable { public: // nsIAccessibleSelectable - NS_IMETHOD GetSelectedItems(nsIArray** aSelectedItems) MOZ_FINAL; - NS_IMETHOD GetSelectedItemCount(uint32_t* aSelectedItemCount) MOZ_FINAL; - NS_IMETHOD GetSelectedItemAt(uint32_t aIndex, nsIAccessible** aItem) MOZ_FINAL; - NS_IMETHOD IsItemSelected(uint32_t aIndex, bool* aIsSelected) MOZ_FINAL; - NS_IMETHOD AddItemToSelection(uint32_t aIndex) MOZ_FINAL; - NS_IMETHOD RemoveItemFromSelection(uint32_t aIndex) MOZ_FINAL; - NS_IMETHOD SelectAll(bool* aIsMultiSelect) MOZ_FINAL; - NS_IMETHOD UnselectAll() MOZ_FINAL; + NS_IMETHOD GetSelectedItems(nsIArray** aSelectedItems) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSelectedItemCount(uint32_t* aSelectedItemCount) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSelectedItemAt(uint32_t aIndex, nsIAccessible** aItem) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD IsItemSelected(uint32_t aIndex, bool* aIsSelected) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD AddItemToSelection(uint32_t aIndex) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD RemoveItemFromSelection(uint32_t aIndex) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD SelectAll(bool* aIsMultiSelect) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD UnselectAll() MOZ_FINAL MOZ_OVERRIDE; protected: xpcAccessibleSelectable() { } diff --git a/accessible/xpcom/xpcAccessibleTable.h b/accessible/xpcom/xpcAccessibleTable.h index d5a16910660..2e835badf80 100644 --- a/accessible/xpcom/xpcAccessibleTable.h +++ b/accessible/xpcom/xpcAccessibleTable.h @@ -26,42 +26,55 @@ public: NS_DECL_ISUPPORTS_INHERITED // nsIAccessibleTable - NS_IMETHOD GetCaption(nsIAccessible** aCaption) MOZ_FINAL; - NS_IMETHOD GetSummary(nsAString& aSummary) MOZ_FINAL; - NS_IMETHOD GetColumnCount(int32_t* aColumnCount) MOZ_FINAL; - NS_IMETHOD GetRowCount(int32_t* aRowCount) MOZ_FINAL; + NS_IMETHOD GetCaption(nsIAccessible** aCaption) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSummary(nsAString& aSummary) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetColumnCount(int32_t* aColumnCount) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRowCount(int32_t* aRowCount) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetCellAt(int32_t aRowIndex, int32_t aColumnIndex, - nsIAccessible** aCell) MOZ_FINAL; + nsIAccessible** aCell) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetCellIndexAt(int32_t aRowIndex, int32_t aColumnIndex, - int32_t* aCellIndex) MOZ_FINAL; - NS_IMETHOD GetColumnIndexAt(int32_t aCellIndex, int32_t* aColumnIndex) MOZ_FINAL; - NS_IMETHOD GetRowIndexAt(int32_t aCellIndex, int32_t* aRowIndex) MOZ_FINAL; + int32_t* aCellIndex) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetColumnIndexAt(int32_t aCellIndex, int32_t* aColumnIndex) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRowIndexAt(int32_t aCellIndex, int32_t* aRowIndex) + MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetRowAndColumnIndicesAt(int32_t aCellIndex, int32_t* aRowIndex, - int32_t* aColumnIndex) MOZ_FINAL; + int32_t* aColumnIndex) + MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetColumnExtentAt(int32_t row, int32_t column, - int32_t* aColumnExtent) MOZ_FINAL; + int32_t* aColumnExtent) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetRowExtentAt(int32_t row, int32_t column, - int32_t* aRowExtent) MOZ_FINAL; - NS_IMETHOD GetColumnDescription(int32_t aColIdx, nsAString& aDescription) MOZ_FINAL; - NS_IMETHOD GetRowDescription(int32_t aRowIdx, nsAString& aDescription) MOZ_FINAL; - NS_IMETHOD IsColumnSelected(int32_t aColIdx, bool* _retval) MOZ_FINAL; - NS_IMETHOD IsRowSelected(int32_t aRowIdx, bool* _retval) MOZ_FINAL; - NS_IMETHOD IsCellSelected(int32_t aRowIdx, int32_t aColIdx, bool* _retval) MOZ_FINAL; - NS_IMETHOD GetSelectedCellCount(uint32_t* aSelectedCellCount) MOZ_FINAL; - NS_IMETHOD GetSelectedColumnCount(uint32_t* aSelectedColumnCount) MOZ_FINAL; - NS_IMETHOD GetSelectedRowCount(uint32_t* aSelectedRowCount) MOZ_FINAL; - NS_IMETHOD GetSelectedCells(nsIArray** aSelectedCell) MOZ_FINAL; + int32_t* aRowExtent) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetColumnDescription(int32_t aColIdx, nsAString& aDescription) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRowDescription(int32_t aRowIdx, nsAString& aDescription) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD IsColumnSelected(int32_t aColIdx, bool* _retval) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD IsRowSelected(int32_t aRowIdx, bool* _retval) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD IsCellSelected(int32_t aRowIdx, int32_t aColIdx, bool* _retval) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSelectedCellCount(uint32_t* aSelectedCellCount) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSelectedColumnCount(uint32_t* aSelectedColumnCount) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSelectedRowCount(uint32_t* aSelectedRowCount) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSelectedCells(nsIArray** aSelectedCell) MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetSelectedCellIndices(uint32_t* aCellsArraySize, - int32_t** aCellsArray) MOZ_FINAL; + int32_t** aCellsArray) + MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetSelectedColumnIndices(uint32_t* aColsArraySize, - int32_t** aColsArray) MOZ_FINAL; + int32_t** aColsArray) + MOZ_FINAL MOZ_OVERRIDE; NS_IMETHOD GetSelectedRowIndices(uint32_t* aRowsArraySize, - int32_t** aRowsArray) MOZ_FINAL; - NS_IMETHOD SelectColumn(int32_t aColIdx) MOZ_FINAL; - NS_IMETHOD SelectRow(int32_t aRowIdx) MOZ_FINAL; - NS_IMETHOD UnselectColumn(int32_t aColIdx) MOZ_FINAL; - NS_IMETHOD UnselectRow(int32_t aRowIdx) MOZ_FINAL; - NS_IMETHOD IsProbablyForLayout(bool* aIsForLayout) MOZ_FINAL; + int32_t** aRowsArray) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD SelectColumn(int32_t aColIdx) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD SelectRow(int32_t aRowIdx) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD UnselectColumn(int32_t aColIdx) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD UnselectRow(int32_t aRowIdx) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD IsProbablyForLayout(bool* aIsForLayout) MOZ_FINAL MOZ_OVERRIDE; protected: virtual ~xpcAccessibleTable() {} diff --git a/accessible/xpcom/xpcAccessibleTableCell.h b/accessible/xpcom/xpcAccessibleTableCell.h index c5f22d0a680..4f99a83ee04 100644 --- a/accessible/xpcom/xpcAccessibleTableCell.h +++ b/accessible/xpcom/xpcAccessibleTableCell.h @@ -27,14 +27,14 @@ public: NS_DECL_ISUPPORTS_INHERITED // nsIAccessibleTableCell - NS_IMETHOD GetTable(nsIAccessibleTable** aTable) MOZ_FINAL; - NS_IMETHOD GetColumnIndex(int32_t* aColIdx) MOZ_FINAL; - NS_IMETHOD GetRowIndex(int32_t* aRowIdx) MOZ_FINAL; - NS_IMETHOD GetColumnExtent(int32_t* aExtent) MOZ_FINAL; - NS_IMETHOD GetRowExtent(int32_t* aExtent) MOZ_FINAL; - NS_IMETHOD GetColumnHeaderCells(nsIArray** aHeaderCells) MOZ_FINAL; - NS_IMETHOD GetRowHeaderCells(nsIArray** aHeaderCells) MOZ_FINAL; - NS_IMETHOD IsSelected(bool* aSelected) MOZ_FINAL; + NS_IMETHOD GetTable(nsIAccessibleTable** aTable) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetColumnIndex(int32_t* aColIdx) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRowIndex(int32_t* aRowIdx) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetColumnExtent(int32_t* aExtent) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRowExtent(int32_t* aExtent) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetColumnHeaderCells(nsIArray** aHeaderCells) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetRowHeaderCells(nsIArray** aHeaderCells) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD IsSelected(bool* aSelected) MOZ_FINAL MOZ_OVERRIDE; protected: virtual ~xpcAccessibleTableCell() {} diff --git a/accessible/xul/XULFormControlAccessible.h b/accessible/xul/XULFormControlAccessible.h index 3124b09e624..7c4856b43ad 100644 --- a/accessible/xul/XULFormControlAccessible.h +++ b/accessible/xul/XULFormControlAccessible.h @@ -174,8 +174,8 @@ public: XULToolbarButtonAccessible(nsIContent* aContent, DocAccessible* aDoc); // Accessible - virtual void GetPositionAndSizeInternal(int32_t *aPosInSet, - int32_t *aSetSize); + virtual void GetPositionAndSizeInternal(int32_t* aPosInSet, + int32_t* aSetSize) MOZ_OVERRIDE; // nsXULToolbarButtonAccessible static bool IsSeparator(Accessible* aAccessible); diff --git a/accessible/xul/XULTreeAccessible.h b/accessible/xul/XULTreeAccessible.h index faeb7f76645..8969fc993dc 100644 --- a/accessible/xul/XULTreeAccessible.h +++ b/accessible/xul/XULTreeAccessible.h @@ -262,7 +262,8 @@ protected: // Accessible virtual Accessible* GetSiblingAtOffset(int32_t aOffset, - nsresult *aError = nullptr) const; + nsresult* aError = nullptr) const + MOZ_OVERRIDE; }; diff --git a/b2g/app/b2g.js b/b2g/app/b2g.js index ac24677a863..f6c6931f586 100644 --- a/b2g/app/b2g.js +++ b/b2g/app/b2g.js @@ -322,7 +322,7 @@ pref("media.fragmented-mp4.gonk.enabled", true); pref("media.video-queue.default-size", 3); // optimize images' memory usage -pref("image.mem.decodeondraw", true); +pref("image.mem.decodeondraw", false); pref("image.mem.allow_locking_in_content_processes", false); /* don't allow image locking */ // Limit the surface cache to 1/8 of main memory or 128MB, whichever is smaller. // Almost everything that was factored into 'max_decoded_image_kb' is now stored diff --git a/b2g/app/nsBrowserApp.cpp b/b2g/app/nsBrowserApp.cpp index 15512cbd704..b7fcea85f5d 100644 --- a/b2g/app/nsBrowserApp.cpp +++ b/b2g/app/nsBrowserApp.cpp @@ -223,6 +223,8 @@ int main(int argc, _CONST char* argv[]) #elif defined(XP_WIN) IO_COUNTERS ioCounters; gotCounters = GetProcessIoCounters(GetCurrentProcess(), &ioCounters); +#else + #error "Unknown platform" // having this here keeps cppcheck happy #endif #ifdef HAS_DLL_BLOCKLIST @@ -271,6 +273,8 @@ int main(int argc, _CONST char* argv[]) XRE_TelemetryAccumulate(mozilla::Telemetry::GLUESTARTUP_HARD_FAULTS, int(newRUsage.ru_majflt - initialRUsage.ru_majflt)); } +#else + #error "Unknown platform" // having this here keeps cppcheck happy #endif } diff --git a/b2g/config/dolphin/sources.xml b/b2g/config/dolphin/sources.xml index 1006df9de48..69dc035d371 100644 --- a/b2g/config/dolphin/sources.xml +++ b/b2g/config/dolphin/sources.xml @@ -15,15 +15,15 @@ - + - + - + @@ -116,7 +116,7 @@ - + diff --git a/b2g/config/emulator-ics/sources.xml b/b2g/config/emulator-ics/sources.xml index 985abdfdbbf..4be3079e07b 100644 --- a/b2g/config/emulator-ics/sources.xml +++ b/b2g/config/emulator-ics/sources.xml @@ -19,13 +19,13 @@ - - + + - + diff --git a/b2g/config/emulator-jb/sources.xml b/b2g/config/emulator-jb/sources.xml index b85f733633e..72d22fa335d 100644 --- a/b2g/config/emulator-jb/sources.xml +++ b/b2g/config/emulator-jb/sources.xml @@ -17,10 +17,10 @@ - - + + - + @@ -118,7 +118,7 @@ - + diff --git a/b2g/config/emulator-kk/sources.xml b/b2g/config/emulator-kk/sources.xml index 36e8ed1041e..fe716455cae 100644 --- a/b2g/config/emulator-kk/sources.xml +++ b/b2g/config/emulator-kk/sources.xml @@ -15,15 +15,15 @@ - + - + - + @@ -116,7 +116,7 @@ - + diff --git a/b2g/config/emulator/sources.xml b/b2g/config/emulator/sources.xml index 985abdfdbbf..4be3079e07b 100644 --- a/b2g/config/emulator/sources.xml +++ b/b2g/config/emulator/sources.xml @@ -19,13 +19,13 @@ - - + + - + diff --git a/b2g/config/flame-kk/sources.xml b/b2g/config/flame-kk/sources.xml index bd7712f222a..7c791615ff5 100644 --- a/b2g/config/flame-kk/sources.xml +++ b/b2g/config/flame-kk/sources.xml @@ -15,15 +15,15 @@ - + - + - + @@ -35,10 +35,8 @@ - - @@ -102,11 +100,8 @@ - - - @@ -116,20 +111,14 @@ - + - - - - - - @@ -137,10 +126,9 @@ - + - diff --git a/b2g/config/flame/sources.xml b/b2g/config/flame/sources.xml index d38ac634079..4225eddd123 100644 --- a/b2g/config/flame/sources.xml +++ b/b2g/config/flame/sources.xml @@ -17,10 +17,10 @@ - - + + - + diff --git a/b2g/config/gaia.json b/b2g/config/gaia.json index 70366070163..0fda39c54a7 100644 --- a/b2g/config/gaia.json +++ b/b2g/config/gaia.json @@ -1,9 +1,9 @@ { "git": { - "git_revision": "", - "remote": "", + "git_revision": "579e01ad4d6e4177a8f636305ac877835d99f134", + "remote": "https://git.mozilla.org/releases/gaia.git", "branch": "" }, - "revision": "11761056b5ee6533ef11443b95a5aee1398e6dd4", + "revision": "91945bbce2f909915fe3edf033215baa4c80e3cd", "repo_path": "integration/gaia-central" } diff --git a/b2g/config/hamachi/sources.xml b/b2g/config/hamachi/sources.xml index ee84abce430..a37b7c249b3 100644 --- a/b2g/config/hamachi/sources.xml +++ b/b2g/config/hamachi/sources.xml @@ -17,11 +17,11 @@ - - + + - + diff --git a/b2g/config/helix/sources.xml b/b2g/config/helix/sources.xml index 36b94249e68..1b4b3d91a3e 100644 --- a/b2g/config/helix/sources.xml +++ b/b2g/config/helix/sources.xml @@ -15,8 +15,8 @@ - - + + diff --git a/b2g/config/nexus-4/sources.xml b/b2g/config/nexus-4/sources.xml index 4e9f312c0ce..cbc53cf5124 100644 --- a/b2g/config/nexus-4/sources.xml +++ b/b2g/config/nexus-4/sources.xml @@ -17,10 +17,10 @@ - - + + - + @@ -118,7 +118,7 @@ - + diff --git a/b2g/config/wasabi/sources.xml b/b2g/config/wasabi/sources.xml index 3251e9d191d..b7108625722 100644 --- a/b2g/config/wasabi/sources.xml +++ b/b2g/config/wasabi/sources.xml @@ -17,12 +17,12 @@ - - + + - + diff --git a/browser/app/nsBrowserApp.cpp b/browser/app/nsBrowserApp.cpp index a44a01a8441..56fb4bb4587 100644 --- a/browser/app/nsBrowserApp.cpp +++ b/browser/app/nsBrowserApp.cpp @@ -613,6 +613,8 @@ int main(int argc, char* argv[]) #elif defined(XP_WIN) IO_COUNTERS ioCounters; gotCounters = GetProcessIoCounters(GetCurrentProcess(), &ioCounters); +#else + #error "Unknown platform" // having this here keeps cppcheck happy #endif nsIFile *xreDirectory; @@ -657,6 +659,8 @@ int main(int argc, char* argv[]) XRE_TelemetryAccumulate(mozilla::Telemetry::GLUESTARTUP_HARD_FAULTS, int(newRUsage.ru_majflt - initialRUsage.ru_majflt)); } +#else + #error "Unknown platform" // having this here keeps cppcheck happy #endif } diff --git a/build/clang-plugin/clang-plugin.cpp b/build/clang-plugin/clang-plugin.cpp index f4dd631787a..c6e1e7ec1e0 100644 --- a/build/clang-plugin/clang-plugin.cpp +++ b/build/clang-plugin/clang-plugin.cpp @@ -220,7 +220,7 @@ public: } } - if (isInterestingDecl(d)) { + if (!d->isAbstract() && isInterestingDecl(d)) { for (CXXRecordDecl::ctor_iterator ctor = d->ctor_begin(), e = d->ctor_end(); ctor != e; ++ctor) { // Ignore non-converting ctors @@ -241,7 +241,10 @@ public: } unsigned ctorID = Diag.getDiagnosticIDs()->getCustomDiagID( DiagnosticIDs::Error, "bad implicit conversion constructor for %0"); + unsigned noteID = Diag.getDiagnosticIDs()->getCustomDiagID( + DiagnosticIDs::Note, "consider adding the explicit keyword to the constructor"); Diag.Report(ctor->getLocation(), ctorID) << d->getDeclName(); + Diag.Report(ctor->getLocation(), noteID); } } diff --git a/build/clang-plugin/tests/TestBadImplicitConversionCtor.cpp b/build/clang-plugin/tests/TestBadImplicitConversionCtor.cpp index cf2aaa140ca..cee6479fa30 100644 --- a/build/clang-plugin/tests/TestBadImplicitConversionCtor.cpp +++ b/build/clang-plugin/tests/TestBadImplicitConversionCtor.cpp @@ -1,9 +1,9 @@ #define MOZ_IMPLICIT __attribute__((annotate("moz_implicit"))) struct Foo { - Foo(int); // expected-error {{bad implicit conversion constructor for 'Foo'}} - Foo(int, char=0); // expected-error {{bad implicit conversion constructor for 'Foo'}} - Foo(...); // expected-error {{bad implicit conversion constructor for 'Foo'}} + Foo(int); // expected-error {{bad implicit conversion constructor for 'Foo'}} expected-note {{consider adding the explicit keyword to the constructor}} + Foo(int, char=0); // expected-error {{bad implicit conversion constructor for 'Foo'}} expected-note {{consider adding the explicit keyword to the constructor}} + Foo(...); // expected-error {{bad implicit conversion constructor for 'Foo'}} expected-note {{consider adding the explicit keyword to the constructor}} Foo(int, unsigned); Foo(Foo&); Foo(const Foo&); @@ -32,3 +32,10 @@ struct Barn { Barn(int, char=0) = delete; Barn(...) = delete; }; + +struct Abstract { + Abstract(int); + Abstract(int, char=0); + Abstract(...); + virtual void f() = 0; +}; diff --git a/dom/base/Element.h b/dom/base/Element.h index 5a22e393861..44f24627fc5 100644 --- a/dom/base/Element.h +++ b/dom/base/Element.h @@ -1296,7 +1296,7 @@ public: nsIContent* aContent, nsIDocument* aDoc); - NS_IMETHOD Run(); + NS_IMETHOD Run() MOZ_OVERRIDE; private: virtual ~RemoveFromBindingManagerRunnable(); nsRefPtr mManager; diff --git a/dom/base/nsContentList.cpp b/dom/base/nsContentList.cpp index bcdf11abe58..7485df9efad 100644 --- a/dom/base/nsContentList.cpp +++ b/dom/base/nsContentList.cpp @@ -215,14 +215,14 @@ NS_GetContentList(nsINode* aRootNode, }; // Initialize the hashtable if needed. - if (!gContentListHashTable.ops) { + if (!gContentListHashTable.IsInitialized()) { PL_DHashTableInit(&gContentListHashTable, &hash_table_ops, sizeof(ContentListHashEntry)); } ContentListHashEntry *entry = nullptr; // First we look in our hashtable. Then we create a content list if needed - if (gContentListHashTable.ops) { + if (gContentListHashTable.IsInitialized()) { // A PL_DHASH_ADD is equivalent to a PL_DHASH_LOOKUP for cases // when the entry is already in the hashtable. @@ -325,14 +325,14 @@ GetFuncStringContentList(nsINode* aRootNode, }; // Initialize the hashtable if needed. - if (!gFuncStringContentListHashTable.ops) { + if (!gFuncStringContentListHashTable.IsInitialized()) { PL_DHashTableInit(&gFuncStringContentListHashTable, &hash_table_ops, sizeof(FuncStringContentListHashEntry)); } FuncStringContentListHashEntry *entry = nullptr; // First we look in our hashtable. Then we create a content list if needed - if (gFuncStringContentListHashTable.ops) { + if (gFuncStringContentListHashTable.IsInitialized()) { nsFuncStringCacheKey hashKey(aRootNode, aFunc, aString); // A PL_DHASH_ADD is equivalent to a PL_DHASH_LOOKUP for cases @@ -977,14 +977,13 @@ nsContentList::RemoveFromHashtable() sRecentlyUsedContentLists[recentlyUsedCacheIndex] = nullptr; } - if (!gContentListHashTable.ops) + if (!gContentListHashTable.IsInitialized()) return; PL_DHashTableRemove(&gContentListHashTable, &key); if (gContentListHashTable.EntryCount() == 0) { PL_DHashTableFinish(&gContentListHashTable); - gContentListHashTable.ops = nullptr; } } @@ -1016,7 +1015,7 @@ nsCacheableFuncStringContentList::~nsCacheableFuncStringContentList() void nsCacheableFuncStringContentList::RemoveFromFuncStringHashtable() { - if (!gFuncStringContentListHashTable.ops) { + if (!gFuncStringContentListHashTable.IsInitialized()) { return; } @@ -1025,7 +1024,6 @@ nsCacheableFuncStringContentList::RemoveFromFuncStringHashtable() if (gFuncStringContentListHashTable.EntryCount() == 0) { PL_DHashTableFinish(&gFuncStringContentListHashTable); - gFuncStringContentListHashTable.ops = nullptr; } } diff --git a/dom/base/nsContentUtils.cpp b/dom/base/nsContentUtils.cpp index 058d048b058..dde489d71b0 100644 --- a/dom/base/nsContentUtils.cpp +++ b/dom/base/nsContentUtils.cpp @@ -344,7 +344,7 @@ public: { // We don't measure the |EventListenerManager| objects pointed to by the // entries because those references are non-owning. - int64_t amount = sEventListenerManagersHash.ops + int64_t amount = sEventListenerManagersHash.IsInitialized() ? PL_DHashTableSizeOfExcludingThis( &sEventListenerManagersHash, nullptr, MallocSizeOf) : 0; @@ -476,7 +476,7 @@ nsContentUtils::Init() if (!InitializeEventTable()) return NS_ERROR_FAILURE; - if (!sEventListenerManagersHash.ops) { + if (!sEventListenerManagersHash.IsInitialized()) { static const PLDHashTableOps hash_table_ops = { PL_DHashVoidPtrKeyStub, @@ -1761,7 +1761,7 @@ nsContentUtils::Shutdown() delete sUserDefinedEvents; sUserDefinedEvents = nullptr; - if (sEventListenerManagersHash.ops) { + if (sEventListenerManagersHash.IsInitialized()) { NS_ASSERTION(sEventListenerManagersHash.EntryCount() == 0, "Event listener manager hash not empty at shutdown!"); @@ -1776,7 +1776,6 @@ nsContentUtils::Shutdown() if (sEventListenerManagersHash.EntryCount() == 0) { PL_DHashTableFinish(&sEventListenerManagersHash); - sEventListenerManagersHash.ops = nullptr; } } @@ -3911,7 +3910,7 @@ ListenerEnumerator(PLDHashTable* aTable, PLDHashEntryHdr* aEntry, void nsContentUtils::UnmarkGrayJSListenersInCCGenerationDocuments(uint32_t aGeneration) { - if (sEventListenerManagersHash.ops) { + if (sEventListenerManagersHash.IsInitialized()) { PL_DHashTableEnumerate(&sEventListenerManagersHash, ListenerEnumerator, &aGeneration); } @@ -3922,7 +3921,7 @@ void nsContentUtils::TraverseListenerManager(nsINode *aNode, nsCycleCollectionTraversalCallback &cb) { - if (!sEventListenerManagersHash.ops) { + if (!sEventListenerManagersHash.IsInitialized()) { // We're already shut down, just return. return; } @@ -3939,7 +3938,7 @@ nsContentUtils::TraverseListenerManager(nsINode *aNode, EventListenerManager* nsContentUtils::GetListenerManagerForNode(nsINode *aNode) { - if (!sEventListenerManagersHash.ops) { + if (!sEventListenerManagersHash.IsInitialized()) { // We're already shut down, don't bother creating an event listener // manager. @@ -3970,7 +3969,7 @@ nsContentUtils::GetExistingListenerManagerForNode(const nsINode *aNode) return nullptr; } - if (!sEventListenerManagersHash.ops) { + if (!sEventListenerManagersHash.IsInitialized()) { // We're already shut down, don't bother creating an event listener // manager. @@ -3991,7 +3990,7 @@ nsContentUtils::GetExistingListenerManagerForNode(const nsINode *aNode) void nsContentUtils::RemoveListenerManager(nsINode *aNode) { - if (sEventListenerManagersHash.ops) { + if (sEventListenerManagersHash.IsInitialized()) { EventListenerManagerMapEntry *entry = static_cast (PL_DHashTableLookup(&sEventListenerManagersHash, aNode)); diff --git a/dom/base/nsDocument.cpp b/dom/base/nsDocument.cpp index 0b3797929cf..ee1cc2013fe 100644 --- a/dom/base/nsDocument.cpp +++ b/dom/base/nsDocument.cpp @@ -2032,7 +2032,7 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INTERNAL(nsDocument) tmp->mAnimationController->Traverse(&cb); } - if (tmp->mSubDocuments && tmp->mSubDocuments->ops) { + if (tmp->mSubDocuments && tmp->mSubDocuments->IsInitialized()) { PL_DHashTableEnumerate(tmp->mSubDocuments, SubDocTraverser, &cb); } diff --git a/dom/base/nsFrameMessageManager.h b/dom/base/nsFrameMessageManager.h index 915feba2cf0..758643459bc 100644 --- a/dom/base/nsFrameMessageManager.h +++ b/dom/base/nsFrameMessageManager.h @@ -148,7 +148,8 @@ public: { } - bool ToObject(JSContext* aCx, JS::MutableHandle aObjp); + virtual bool ToObject(JSContext* aCx, JS::MutableHandle aObjp) + MOZ_OVERRIDE; private: JS::Rooted mObj; diff --git a/dom/base/nsJSEnvironment.h b/dom/base/nsJSEnvironment.h index d090549d360..17bf0335a6c 100644 --- a/dom/base/nsJSEnvironment.h +++ b/dom/base/nsJSEnvironment.h @@ -192,7 +192,7 @@ public: : mReport(aReport) {} - NS_IMETHOD Run() + NS_IMETHOD Run() MOZ_OVERRIDE { mReport->LogToConsole(); return NS_OK; diff --git a/dom/base/nsPropertyTable.cpp b/dom/base/nsPropertyTable.cpp index ed17f35a28e..886ee4f0379 100644 --- a/dom/base/nsPropertyTable.cpp +++ b/dom/base/nsPropertyTable.cpp @@ -215,7 +215,7 @@ nsPropertyTable::SetPropertyInternal(nsPropertyOwner aObject, } else { propertyList = new PropertyList(aPropertyName, aPropDtorFunc, aPropDtorData, aTransfer); - if (!propertyList || !propertyList->mObjectValueMap.ops) { + if (!propertyList || !propertyList->mObjectValueMap.IsInitialized()) { delete propertyList; return NS_ERROR_OUT_OF_MEMORY; } diff --git a/dom/bluetooth/BluetoothCommon.h b/dom/bluetooth/BluetoothCommon.h index cdee8da18c7..abdbef81e52 100644 --- a/dom/bluetooth/BluetoothCommon.h +++ b/dom/bluetooth/BluetoothCommon.h @@ -53,8 +53,8 @@ extern bool gBluetoothDebugFlag; } \ } while(0) -#define BT_LOGR(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__)) -#define BT_WARNING(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__)) +#define BT_LOGR(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__) +#define BT_WARNING(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__) #endif /** diff --git a/dom/bluetooth/bluedroid/BluetoothDaemonInterface.cpp b/dom/bluetooth/bluedroid/BluetoothDaemonInterface.cpp index 715c99a6281..7c41a8ef644 100644 --- a/dom/bluetooth/bluedroid/BluetoothDaemonInterface.cpp +++ b/dom/bluetooth/bluedroid/BluetoothDaemonInterface.cpp @@ -5,6 +5,9 @@ * You can obtain one at http://mozilla.org/MPL/2.0/. */ #include "BluetoothDaemonInterface.h" +#include +#include +#include #include "BluetoothDaemonA2dpInterface.h" #include "BluetoothDaemonAvrcpInterface.h" #include "BluetoothDaemonHandsfreeInterface.h" @@ -12,7 +15,10 @@ #include "BluetoothDaemonSetupInterface.h" #include "BluetoothDaemonSocketInterface.h" #include "BluetoothInterfaceHelpers.h" +#include "mozilla/ipc/ListenSocket.h" +#include "mozilla/ipc/UnixSocketConnector.h" #include "mozilla/unused.h" +#include "prrng.h" using namespace mozilla::ipc; @@ -1431,7 +1437,9 @@ class BluetoothDaemonProtocol MOZ_FINAL , public BluetoothDaemonAvrcpModule { public: - BluetoothDaemonProtocol(BluetoothDaemonConnection* aConnection); + BluetoothDaemonProtocol(); + + void SetConnection(BluetoothDaemonConnection* aConnection); nsresult RegisterModule(uint8_t aId, uint8_t aMode, uint32_t aMaxNumClients, BluetoothSetupResultHandler* aRes) MOZ_OVERRIDE; @@ -1471,11 +1479,13 @@ private: nsTArray mUserDataQ; }; -BluetoothDaemonProtocol::BluetoothDaemonProtocol( - BluetoothDaemonConnection* aConnection) - : mConnection(aConnection) +BluetoothDaemonProtocol::BluetoothDaemonProtocol() +{ } + +void +BluetoothDaemonProtocol::SetConnection(BluetoothDaemonConnection* aConnection) { - MOZ_ASSERT(mConnection); + mConnection = aConnection; } nsresult @@ -1497,6 +1507,7 @@ BluetoothDaemonProtocol::UnregisterModule(uint8_t aId, nsresult BluetoothDaemonProtocol::Send(BluetoothDaemonPDU* aPDU, void* aUserData) { + MOZ_ASSERT(mConnection); MOZ_ASSERT(aPDU); aPDU->SetUserData(aUserData); @@ -1606,16 +1617,13 @@ BluetoothDaemonProtocol::FetchUserData(const BluetoothDaemonPDUHeader& aHeader) } // -// Channels +// Listen socket // -class BluetoothDaemonChannel MOZ_FINAL : public BluetoothDaemonConnection +class BluetoothDaemonListenSocket MOZ_FINAL : public ipc::ListenSocket { public: - BluetoothDaemonChannel(BluetoothDaemonInterface::Channel aChannel); - - nsresult ConnectSocket(BluetoothDaemonInterface* aInterface, - BluetoothDaemonPDUConsumer* aConsumer); + BluetoothDaemonListenSocket(BluetoothDaemonInterface* aInterface); // Connection state // @@ -1624,28 +1632,80 @@ public: void OnConnectError() MOZ_OVERRIDE; void OnDisconnect() MOZ_OVERRIDE; +private: + BluetoothDaemonInterface* mInterface; +}; + +BluetoothDaemonListenSocket::BluetoothDaemonListenSocket( + BluetoothDaemonInterface* aInterface) + : mInterface(aInterface) +{ } + +void +BluetoothDaemonListenSocket::OnConnectSuccess() +{ + MOZ_ASSERT(NS_IsMainThread()); + MOZ_ASSERT(mInterface); + + mInterface->OnConnectSuccess(BluetoothDaemonInterface::LISTEN_SOCKET); +} + +void +BluetoothDaemonListenSocket::OnConnectError() +{ + MOZ_ASSERT(NS_IsMainThread()); + MOZ_ASSERT(mInterface); + + mInterface->OnConnectError(BluetoothDaemonInterface::LISTEN_SOCKET); +} + +void +BluetoothDaemonListenSocket::OnDisconnect() +{ + MOZ_ASSERT(NS_IsMainThread()); + MOZ_ASSERT(mInterface); + + mInterface->OnDisconnect(BluetoothDaemonInterface::LISTEN_SOCKET); +} + +// +// Channels +// + +class BluetoothDaemonChannel MOZ_FINAL : public BluetoothDaemonConnection +{ +public: + BluetoothDaemonChannel(BluetoothDaemonInterface* aInterface, + BluetoothDaemonInterface::Channel aChannel, + BluetoothDaemonPDUConsumer* aConsumer); + + // SocketBase + // + + void OnConnectSuccess() MOZ_OVERRIDE; + void OnConnectError() MOZ_OVERRIDE; + void OnDisconnect() MOZ_OVERRIDE; + + // ConnectionOrientedSocket + // + + ConnectionOrientedSocketIO* GetIO() MOZ_OVERRIDE; + private: BluetoothDaemonInterface* mInterface; BluetoothDaemonInterface::Channel mChannel; + BluetoothDaemonPDUConsumer* mConsumer; }; BluetoothDaemonChannel::BluetoothDaemonChannel( - BluetoothDaemonInterface::Channel aChannel) -: mInterface(nullptr) -, mChannel(aChannel) + BluetoothDaemonInterface* aInterface, + BluetoothDaemonInterface::Channel aChannel, + BluetoothDaemonPDUConsumer* aConsumer) + : mInterface(aInterface) + , mChannel(aChannel) + , mConsumer(aConsumer) { } -nsresult -BluetoothDaemonChannel::ConnectSocket(BluetoothDaemonInterface* aInterface, - BluetoothDaemonPDUConsumer* aConsumer) -{ - MOZ_ASSERT(aInterface); - - mInterface = aInterface; - - return BluetoothDaemonConnection::ConnectSocket(aConsumer); -} - void BluetoothDaemonChannel::OnConnectSuccess() { @@ -1662,7 +1722,6 @@ BluetoothDaemonChannel::OnConnectError() MOZ_ASSERT(mInterface); mInterface->OnConnectError(mChannel); - mInterface = nullptr; } void @@ -1672,7 +1731,12 @@ BluetoothDaemonChannel::OnDisconnect() MOZ_ASSERT(mInterface); mInterface->OnDisconnect(mChannel); - mInterface = nullptr; +} + +ConnectionOrientedSocketIO* +BluetoothDaemonChannel::GetIO() +{ + return PrepareAccept(mConsumer); } // @@ -1694,38 +1758,13 @@ BluetoothDaemonInterface::GetInstance() return sBluetoothInterface; } - // Only create channel objects here. The connection will be - // established by |BluetoothDaemonInterface::Init|. - - BluetoothDaemonChannel* cmdChannel = - new BluetoothDaemonChannel(BluetoothDaemonInterface::CMD_CHANNEL); - - BluetoothDaemonChannel* ntfChannel = - new BluetoothDaemonChannel(BluetoothDaemonInterface::NTF_CHANNEL); - - // Create a new interface object with the channels and a - // protocol handler. - - sBluetoothInterface = - new BluetoothDaemonInterface(cmdChannel, - ntfChannel, - new BluetoothDaemonProtocol(cmdChannel)); + sBluetoothInterface = new BluetoothDaemonInterface(); return sBluetoothInterface; } -BluetoothDaemonInterface::BluetoothDaemonInterface( - BluetoothDaemonChannel* aCmdChannel, - BluetoothDaemonChannel* aNtfChannel, - BluetoothDaemonProtocol* aProtocol) -: mCmdChannel(aCmdChannel) -, mNtfChannel(aNtfChannel) -, mProtocol(aProtocol) -{ - MOZ_ASSERT(mCmdChannel); - MOZ_ASSERT(mNtfChannel); - MOZ_ASSERT(mProtocol); -} +BluetoothDaemonInterface::BluetoothDaemonInterface() +{ } BluetoothDaemonInterface::~BluetoothDaemonInterface() { } @@ -1763,11 +1802,11 @@ public: if (!mRegisteredSocketModule) { mRegisteredSocketModule = true; - // Init, step 4: Register Socket module + // Init, step 5: Register Socket module mInterface->mProtocol->RegisterModuleCmd(0x02, 0x00, BluetoothDaemonSocketModule::MAX_NUM_CLIENTS, this); } else if (mRes) { - // Init, step 5: Signal success to caller + // Init, step 6: Signal success to caller mRes->Init(); } } @@ -1785,24 +1824,33 @@ BluetoothDaemonInterface::OnConnectSuccess(enum Channel aChannel) MOZ_ASSERT(!mResultHandlerQ.IsEmpty()); switch (aChannel) { - case CMD_CHANNEL: - // Init, step 2: Connect notification channel... - if (mNtfChannel->GetConnectionStatus() != SOCKET_CONNECTED) { - nsresult rv = mNtfChannel->ConnectSocket(this, mProtocol); - if (NS_FAILED(rv)) { + case LISTEN_SOCKET: { + // Init, step 2: Start Bluetooth daemon */ + nsCString value("bluetoothd:-a "); + value.Append(mListenSocketName); + if (NS_WARN_IF(property_set("ctl.start", value.get()) < 0)) { OnConnectError(CMD_CHANNEL); } - } else { - // ...or go to step 3 if channel is already connected. - OnConnectSuccess(NTF_CHANNEL); } break; - + case CMD_CHANNEL: + // Init, step 3: Listen for notification channel... + if (!mNtfChannel) { + mNtfChannel = new BluetoothDaemonChannel(this, NTF_CHANNEL, mProtocol); + } else if ( + NS_WARN_IF(mNtfChannel->GetConnectionStatus() == SOCKET_CONNECTED)) { + /* Notification channel should not be open; let's close it. */ + mNtfChannel->CloseSocket(); + } + if (!mListenSocket->Listen(mNtfChannel)) { + OnConnectError(NTF_CHANNEL); + } + break; case NTF_CHANNEL: { nsRefPtr res = mResultHandlerQ.ElementAt(0); mResultHandlerQ.RemoveElementAt(0); - // Init, step 3: Register Core module + // Init, step 4: Register Core module nsresult rv = mProtocol->RegisterModuleCmd( 0x01, 0x00, BluetoothDaemonCoreModule::MAX_NUM_CLIENTS, new InitResultHandler(this, res)); @@ -1824,7 +1872,11 @@ BluetoothDaemonInterface::OnConnectError(enum Channel aChannel) case NTF_CHANNEL: // Close command channel mCmdChannel->CloseSocket(); - case CMD_CHANNEL: { + case CMD_CHANNEL: + // Stop daemon and close listen socket + unused << NS_WARN_IF(property_set("ctl.stop", "bluetoothd")); + mListenSocket->Close(); + case LISTEN_SOCKET: { // Signal error to caller nsRefPtr res = mResultHandlerQ.ElementAt(0); mResultHandlerQ.RemoveElementAt(0); @@ -1844,11 +1896,15 @@ BluetoothDaemonInterface::OnDisconnect(enum Channel aChannel) MOZ_ASSERT(!mResultHandlerQ.IsEmpty()); switch (aChannel) { - case NTF_CHANNEL: - // Cleanup, step 4: Close command channel - mCmdChannel->CloseSocket(); + case CMD_CHANNEL: + // We don't have to do anything here. Step 4 is triggered + // by the daemon. break; - case CMD_CHANNEL: { + case NTF_CHANNEL: + // Cleanup, step 4: Close listen socket + mListenSocket->Close(); + break; + case LISTEN_SOCKET: { nsRefPtr res = mResultHandlerQ.ElementAt(0); mResultHandlerQ.RemoveElementAt(0); @@ -1861,25 +1917,207 @@ BluetoothDaemonInterface::OnDisconnect(enum Channel aChannel) } } +class BluetoothDaemonSocketConnector MOZ_FINAL + : public mozilla::ipc::UnixSocketConnector +{ +public: + BluetoothDaemonSocketConnector(const nsACString& aSocketName) + : mSocketName(aSocketName) + { } + + int + Create() MOZ_OVERRIDE + { + MOZ_ASSERT(!NS_IsMainThread()); + + int fd = socket(AF_UNIX, SOCK_SEQPACKET, 0); + if (fd < 0) { + BT_WARNING("Could not open socket!"); + return -1; + } + return fd; + } + + bool + CreateAddr(bool aIsServer, + socklen_t& aAddrSize, + sockaddr_any& aAddr, + const char* aAddress) MOZ_OVERRIDE + { + static const size_t sNameOffset = 1; + + size_t namesiz = mSocketName.Length() + 1; /* include trailing '\0' */ + + if ((sNameOffset + namesiz) > sizeof(aAddr.un.sun_path)) { + BT_WARNING("Address too long for socket struct!"); + return false; + } + + memset(aAddr.un.sun_path, '\0', sNameOffset); // abstract socket + memcpy(aAddr.un.sun_path + sNameOffset, mSocketName.get(), namesiz); + aAddr.un.sun_family = AF_UNIX; + + aAddrSize = offsetof(struct sockaddr_un, sun_path) + sNameOffset + namesiz; + + return true; + } + + bool + SetUp(int aFd) MOZ_OVERRIDE + { + if (TEMP_FAILURE_RETRY(fcntl(aFd, F_SETFL, O_NONBLOCK)) < 0) { + BT_WARNING("Failed to set non-blocking I/O."); + return false; + } + return true; + } + + bool + SetUpListenSocket(int aFd) MOZ_OVERRIDE + { + return true; + } + + void + GetSocketAddr(const sockaddr_any& aAddr, nsAString& aAddrStr) MOZ_OVERRIDE + { + // Unused. + MOZ_CRASH("This should never be called!"); + } + +private: + nsCString mSocketName; +}; + +nsresult +BluetoothDaemonInterface::CreateRandomAddressString( + const nsACString& aPrefix, unsigned long aPostfixLength, + nsACString& aAddress) +{ + static const char sHexChar[16] = { + [0x0] = '0', [0x1] = '1', [0x2] = '2', [0x3] = '3', + [0x4] = '4', [0x5] = '5', [0x6] = '6', [0x7] = '7', + [0x8] = '8', [0x9] = '9', [0xa] = 'a', [0xb] = 'b', + [0xc] = 'c', [0xd] = 'd', [0xe] = 'e', [0xf] = 'f' + }; + + unsigned short seed[3]; + + if (NS_WARN_IF(!PR_GetRandomNoise(seed, sizeof(seed)))) { + return NS_ERROR_NOT_IMPLEMENTED; + } + + aAddress = aPrefix; + aAddress.Append('-'); + + while (aPostfixLength) { + + // Android doesn't provide rand_r, so we use nrand48 here, + // even though it's deprecated. + long value = nrand48(seed); + + size_t bits = sizeof(value) * CHAR_BIT; + + while ((bits > 4) && aPostfixLength) { + aAddress.Append(sHexChar[value&0xf]); + bits -= 4; + value >>= 4; + --aPostfixLength; + } + } + + return NS_OK; +} + +/* + * The init procedure consists of several steps. + * + * (1) Start listening for the command channel's socket connection: We + * do this before anything else, so that we don't miss connection + * requests from the Bluetooth daemon. This step will create a + * listen socket. + * + * (2) Start the Bluetooth daemon: When the daemon starts up it will + * open two socket connections to Gecko and thus create the command + * and notification channels. Gecko already opened the listen socket + * in step (1). Step (2) ends with the creation of the command channel. + * + * (3) Start listening for the notification channel's socket connection: + * At the end of step (2), the command channel was opened by the + * daemon. In step (3), the daemon immediately tries to open the + * next socket for the notification channel. Gecko will accept the + * incoming connection request for the notification channel. The + * listen socket remained open after step (2), so there's no race + * condition between Gecko and the Bluetooth daemon. + * + * (4)(5) Register Core and Socket modules: The Core and Socket modules + * are always available and have to be registered after opening the + * socket connections during the initialization. + * + * (6) Signal success to the caller. + * + * If any step fails, we roll-back the procedure and signal an error to the + * caller. + */ void BluetoothDaemonInterface::Init( BluetoothNotificationHandler* aNotificationHandler, BluetoothResultHandler* aRes) { + static const char BASE_SOCKET_NAME[] = "bluetoothd"; + static unsigned long POSTFIX_LENGTH = 16; + + // If we could not cleanup properly before and an old + // instance of the daemon is still running, we kill it + // here. + unused << NS_WARN_IF(property_set("ctl.stop", "bluetoothd")); + sNotificationHandler = aNotificationHandler; mResultHandlerQ.AppendElement(aRes); - // Init, step 1: Connect command channel... - if (mCmdChannel->GetConnectionStatus() != SOCKET_CONNECTED) { - nsresult rv = mCmdChannel->ConnectSocket(this, mProtocol); - if (NS_FAILED(rv)) { - OnConnectError(CMD_CHANNEL); - } - } else { - // ...or go to step 2 if channel is already connected. - OnConnectSuccess(CMD_CHANNEL); + if (!mProtocol) { + mProtocol = new BluetoothDaemonProtocol(); } + + if (!mListenSocket) { + mListenSocket = new BluetoothDaemonListenSocket(this); + } + + // Init, step 1: Listen for command channel... */ + + if (!mCmdChannel) { + mCmdChannel = new BluetoothDaemonChannel(this, CMD_CHANNEL, mProtocol); + } else if ( + NS_WARN_IF(mCmdChannel->GetConnectionStatus() == SOCKET_CONNECTED)) { + // Command channel should not be open; let's close it. + mCmdChannel->CloseSocket(); + } + + // The listen socket's name is generated with a random postfix. This + // avoids naming collisions if we still have a listen socket from a + // previously failed cleanup. It also makes it hard for malicious + // external programs to capture the socket name or connect before + // the daemon can do so. If no random postfix can be generated, we + // simply use the base name as-is. + nsresult rv = CreateRandomAddressString(NS_LITERAL_CSTRING(BASE_SOCKET_NAME), + POSTFIX_LENGTH, + mListenSocketName); + if (NS_FAILED(rv)) { + mListenSocketName = BASE_SOCKET_NAME; + } + + bool success = mListenSocket->Listen( + new BluetoothDaemonSocketConnector(mListenSocketName), mCmdChannel); + if (!success) { + OnConnectError(CMD_CHANNEL); + return; + } + + // The protocol implementation needs a command channel for + // sending commands to the daemon. We set it here, because + // this is the earliest time when it's available. + mProtocol->SetConnection(mCmdChannel); } class BluetoothDaemonInterface::CleanupResultHandler MOZ_FINAL @@ -1914,8 +2152,8 @@ private: // Cleanup, step 2: Unregister Core module mInterface->mProtocol->UnregisterModuleCmd(0x01, this); } else { - // Cleanup, step 3: Close notification channel - mInterface->mNtfChannel->CloseSocket(); + // Cleanup, step 3: Close command channel + mInterface->mCmdChannel->CloseSocket(); } } @@ -1923,6 +2161,31 @@ private: bool mUnregisteredCoreModule; }; +/* + * Cleaning up is inverse to initialization, except for the shutdown + * of the socket connections in step (3) + * + * (1)(2) Unregister Socket and Core modules: These modules have been + * registered during initialization and need to be unregistered + * here. We assume that all other modules are already unregistered. + * + * (3) Close command socket: We only close the command socket. The + * daemon will then send any final notifications and close the + * notification socket on its side. Once we see the notification + * socket's disconnect, we continue with the cleanup. + * + * (4) Close listen socket: The listen socket is not active any longer + * and we simply close it. + * + * (5) Signal success to the caller. + * + * We don't have to stop the daemon explicitly. It will cleanup and quit + * after it closed the notification socket. + * + * Rolling-back half-completed cleanups is not possible. In the case of + * an error, we simply push forward and try to recover during the next + * initialization. + */ void BluetoothDaemonInterface::Cleanup(BluetoothResultHandler* aRes) { diff --git a/dom/bluetooth/bluedroid/BluetoothDaemonInterface.h b/dom/bluetooth/bluedroid/BluetoothDaemonInterface.h index dc094f5e91c..8201e5e4991 100644 --- a/dom/bluetooth/bluedroid/BluetoothDaemonInterface.h +++ b/dom/bluetooth/bluedroid/BluetoothDaemonInterface.h @@ -11,6 +11,7 @@ BEGIN_BLUETOOTH_NAMESPACE +class BluetoothDaemonListenSocket; class BluetoothDaemonChannel; class BluetoothDaemonA2dpInterface; class BluetoothDaemonAvrcpInterface; @@ -24,6 +25,7 @@ public: class CleanupResultHandler; class InitResultHandler; + friend class BluetoothDaemonListenSocket; friend class BluetoothDaemonChannel; friend class CleanupResultHandler; friend class InitResultHandler; @@ -115,24 +117,29 @@ public: protected: enum Channel { + LISTEN_SOCKET, CMD_CHANNEL, NTF_CHANNEL }; - BluetoothDaemonInterface(BluetoothDaemonChannel* aCmdChannel, - BluetoothDaemonChannel* aNtfChannel, - BluetoothDaemonProtocol* aProtocol); + BluetoothDaemonInterface(); ~BluetoothDaemonInterface(); void OnConnectSuccess(enum Channel aChannel); void OnConnectError(enum Channel aChannel); void OnDisconnect(enum Channel aChannel); + nsresult CreateRandomAddressString(const nsACString& aPrefix, + unsigned long aPostfixLength, + nsACString& aAddress); + private: void DispatchError(BluetoothResultHandler* aRes, BluetoothStatus aStatus); - nsAutoPtr mCmdChannel; - nsAutoPtr mNtfChannel; + nsCString mListenSocketName; + nsRefPtr mListenSocket; + nsRefPtr mCmdChannel; + nsRefPtr mNtfChannel; nsAutoPtr mProtocol; nsTArray > mResultHandlerQ; diff --git a/dom/bluetooth2/BluetoothCommon.h b/dom/bluetooth2/BluetoothCommon.h index e7ddb7c28e4..56966cbff77 100644 --- a/dom/bluetooth2/BluetoothCommon.h +++ b/dom/bluetooth2/BluetoothCommon.h @@ -66,8 +66,8 @@ extern bool gBluetoothDebugFlag; } \ } while(0) -#define BT_LOGR(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__)) -#define BT_WARNING(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__)) +#define BT_LOGR(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__) +#define BT_WARNING(msg, ...) printf("%s: " msg, __FUNCTION__, ##__VA_ARGS__) #endif /** diff --git a/dom/bluetooth2/BluetoothPairingListener.cpp b/dom/bluetooth2/BluetoothPairingListener.cpp index 89a9cb790b8..dfb4ebf23e5 100644 --- a/dom/bluetooth2/BluetoothPairingListener.cpp +++ b/dom/bluetooth2/BluetoothPairingListener.cpp @@ -21,13 +21,11 @@ NS_IMPL_RELEASE_INHERITED(BluetoothPairingListener, DOMEventTargetHelper) BluetoothPairingListener::BluetoothPairingListener(nsPIDOMWindow* aWindow) : DOMEventTargetHelper(aWindow) + , mHasListenedToSignal(false) { MOZ_ASSERT(aWindow); - BluetoothService* bs = BluetoothService::Get(); - NS_ENSURE_TRUE_VOID(bs); - bs->RegisterBluetoothSignalHandler(NS_LITERAL_STRING(KEY_PAIRING_LISTENER), - this); + TryListeningToBluetoothSignal(); } already_AddRefed @@ -134,3 +132,39 @@ BluetoothPairingListener::DisconnectFromOwner() bs->UnregisterBluetoothSignalHandler(NS_LITERAL_STRING(KEY_PAIRING_LISTENER), this); } + +void +BluetoothPairingListener::EventListenerAdded(nsIAtom* aType) +{ + DOMEventTargetHelper::EventListenerAdded(aType); + + TryListeningToBluetoothSignal(); +} + +void +BluetoothPairingListener::TryListeningToBluetoothSignal() +{ + if (mHasListenedToSignal) { + // We've handled prior pending pairing requests + return; + } + + // Listen to bluetooth signal only if all pairing event handlers have been + // attached. All pending pairing requests queued in BluetoothService would + // be fired when pairing listener starts listening to bluetooth signal. + if (!HasListenersFor(nsGkAtoms::ondisplaypasskeyreq) || + !HasListenersFor(nsGkAtoms::onenterpincodereq) || + !HasListenersFor(nsGkAtoms::onpairingconfirmationreq) || + !HasListenersFor(nsGkAtoms::onpairingconsentreq)) { + BT_LOGR("Pairing listener is not ready to handle pairing requests!"); + return; + } + + // Start listening to bluetooth signal to handle pairing requests + BluetoothService* bs = BluetoothService::Get(); + NS_ENSURE_TRUE_VOID(bs); + bs->RegisterBluetoothSignalHandler(NS_LITERAL_STRING(KEY_PAIRING_LISTENER), + this); + + mHasListenedToSignal = true; +} diff --git a/dom/bluetooth2/BluetoothPairingListener.h b/dom/bluetooth2/BluetoothPairingListener.h index 909fbc0e695..a9afc7c06a9 100644 --- a/dom/bluetooth2/BluetoothPairingListener.h +++ b/dom/bluetooth2/BluetoothPairingListener.h @@ -38,6 +38,7 @@ public: virtual JSObject* WrapObject(JSContext* aCx) MOZ_OVERRIDE; virtual void DisconnectFromOwner() MOZ_OVERRIDE; + virtual void EventListenerAdded(nsIAtom* aType) MOZ_OVERRIDE; IMPL_EVENT_HANDLER(displaypasskeyreq); IMPL_EVENT_HANDLER(enterpincodereq); @@ -47,6 +48,21 @@ public: private: BluetoothPairingListener(nsPIDOMWindow* aWindow); ~BluetoothPairingListener(); + + /** + * Listen to bluetooth signal if all pairing event handlers are ready. + * + * Listen to bluetooth signal only if all pairing event handlers have been + * attached. All pending pairing requests queued in BluetoothService would be + * fired when pairing listener starts listening to bluetooth signal. + */ + void TryListeningToBluetoothSignal(); + + /** + * Indicate whether or not this pairing listener has started listening to + * Bluetooth signal. + */ + bool mHasListenedToSignal; }; END_BLUETOOTH_NAMESPACE diff --git a/dom/canvas/WebGLContextReporter.cpp b/dom/canvas/WebGLContextReporter.cpp index 1fb1916e33b..b7f88473923 100644 --- a/dom/canvas/WebGLContextReporter.cpp +++ b/dom/canvas/WebGLContextReporter.cpp @@ -126,8 +126,10 @@ WebGLMemoryTracker::GetBufferCacheMemoryUsed() buffer; buffer = buffer->getNext()) { - if (buffer->Target() == LOCAL_GL_ELEMENT_ARRAY_BUFFER) + if (buffer->HasEverBeenBound() && + buffer->Target() == LOCAL_GL_ELEMENT_ARRAY_BUFFER) { result += buffer->SizeOfIncludingThis(WebGLBufferMallocSizeOf); + } } } return result; diff --git a/dom/html/nsGenericHTMLElement.h b/dom/html/nsGenericHTMLElement.h index 0caae6be6bc..f812ae25b3b 100644 --- a/dom/html/nsGenericHTMLElement.h +++ b/dom/html/nsGenericHTMLElement.h @@ -317,25 +317,25 @@ public: NS_FORWARD_NSIDOMELEMENT_TO_GENERIC - NS_IMETHOD GetTitle(nsAString& aTitle) MOZ_FINAL { + NS_IMETHOD GetTitle(nsAString& aTitle) MOZ_FINAL MOZ_OVERRIDE { nsString title; GetTitle(title); aTitle.Assign(title); return NS_OK; } - NS_IMETHOD GetLang(nsAString& aLang) MOZ_FINAL { + NS_IMETHOD GetLang(nsAString& aLang) MOZ_FINAL MOZ_OVERRIDE { nsString lang; GetLang(lang); aLang.Assign(lang); return NS_OK; } - NS_IMETHOD GetDir(nsAString& aDir) MOZ_FINAL { + NS_IMETHOD GetDir(nsAString& aDir) MOZ_FINAL MOZ_OVERRIDE { nsString dir; GetDir(dir); aDir.Assign(dir); return NS_OK; } - NS_IMETHOD SetDir(const nsAString& aDir) MOZ_FINAL { + NS_IMETHOD SetDir(const nsAString& aDir) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetDir(aDir, rv); return rv.ErrorCode(); @@ -348,131 +348,137 @@ public: SetClassName(aClassName); return NS_OK; } - NS_IMETHOD GetDataset(nsISupports** aDataset) MOZ_FINAL; - NS_IMETHOD GetHidden(bool* aHidden) MOZ_FINAL { + NS_IMETHOD GetDataset(nsISupports** aDataset) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetHidden(bool* aHidden) MOZ_FINAL MOZ_OVERRIDE { *aHidden = Hidden(); return NS_OK; } - NS_IMETHOD SetHidden(bool aHidden) MOZ_FINAL { + NS_IMETHOD SetHidden(bool aHidden) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetHidden(aHidden, rv); return rv.ErrorCode(); } - NS_IMETHOD DOMBlur() MOZ_FINAL { + NS_IMETHOD DOMBlur() MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; Blur(rv); return rv.ErrorCode(); } - NS_IMETHOD GetItemScope(bool* aItemScope) MOZ_FINAL { + NS_IMETHOD GetItemScope(bool* aItemScope) MOZ_FINAL MOZ_OVERRIDE { *aItemScope = ItemScope(); return NS_OK; } - NS_IMETHOD SetItemScope(bool aItemScope) MOZ_FINAL { + NS_IMETHOD SetItemScope(bool aItemScope) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetItemScope(aItemScope, rv); return rv.ErrorCode(); } - NS_IMETHOD GetItemType(nsIVariant** aType) MOZ_FINAL { + NS_IMETHOD GetItemType(nsIVariant** aType) MOZ_FINAL MOZ_OVERRIDE { GetTokenList(nsGkAtoms::itemtype, aType); return NS_OK; } - NS_IMETHOD SetItemType(nsIVariant* aType) MOZ_FINAL { + NS_IMETHOD SetItemType(nsIVariant* aType) MOZ_FINAL MOZ_OVERRIDE { return SetTokenList(nsGkAtoms::itemtype, aType); } - NS_IMETHOD GetItemId(nsAString& aId) MOZ_FINAL { + NS_IMETHOD GetItemId(nsAString& aId) MOZ_FINAL MOZ_OVERRIDE { nsString id; GetItemId(id); aId.Assign(aId); return NS_OK; } - NS_IMETHOD SetItemId(const nsAString& aId) MOZ_FINAL { + NS_IMETHOD SetItemId(const nsAString& aId) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetItemId(aId, rv); return rv.ErrorCode(); } - NS_IMETHOD GetProperties(nsISupports** aReturn) MOZ_FINAL; - NS_IMETHOD GetItemValue(nsIVariant** aValue) MOZ_FINAL; - NS_IMETHOD SetItemValue(nsIVariant* aValue) MOZ_FINAL; - NS_IMETHOD GetItemRef(nsIVariant** aRef) MOZ_FINAL { + NS_IMETHOD GetProperties(nsISupports** aReturn) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetItemValue(nsIVariant** aValue) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD SetItemValue(nsIVariant* aValue) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetItemRef(nsIVariant** aRef) MOZ_FINAL MOZ_OVERRIDE { GetTokenList(nsGkAtoms::itemref, aRef); return NS_OK; } - NS_IMETHOD SetItemRef(nsIVariant* aRef) MOZ_FINAL { + NS_IMETHOD SetItemRef(nsIVariant* aRef) MOZ_FINAL MOZ_OVERRIDE { return SetTokenList(nsGkAtoms::itemref, aRef); } - NS_IMETHOD GetItemProp(nsIVariant** aProp) MOZ_FINAL { + NS_IMETHOD GetItemProp(nsIVariant** aProp) MOZ_FINAL MOZ_OVERRIDE { GetTokenList(nsGkAtoms::itemprop, aProp); return NS_OK; } - NS_IMETHOD SetItemProp(nsIVariant* aProp) MOZ_FINAL { + NS_IMETHOD SetItemProp(nsIVariant* aProp) MOZ_FINAL MOZ_OVERRIDE { return SetTokenList(nsGkAtoms::itemprop, aProp); } - NS_IMETHOD GetAccessKey(nsAString& aAccessKey) MOZ_FINAL { + NS_IMETHOD GetAccessKey(nsAString& aAccessKey) MOZ_FINAL MOZ_OVERRIDE { nsString accessKey; GetAccessKey(accessKey); aAccessKey.Assign(accessKey); return NS_OK; } - NS_IMETHOD SetAccessKey(const nsAString& aAccessKey) MOZ_FINAL { + NS_IMETHOD SetAccessKey(const nsAString& aAccessKey) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetAccessKey(aAccessKey, rv); return rv.ErrorCode(); } - NS_IMETHOD GetAccessKeyLabel(nsAString& aAccessKeyLabel) MOZ_FINAL { + NS_IMETHOD GetAccessKeyLabel(nsAString& aAccessKeyLabel) + MOZ_FINAL MOZ_OVERRIDE { nsString accessKeyLabel; GetAccessKeyLabel(accessKeyLabel); aAccessKeyLabel.Assign(accessKeyLabel); return NS_OK; } - NS_IMETHOD SetDraggable(bool aDraggable) MOZ_FINAL { + NS_IMETHOD SetDraggable(bool aDraggable) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetDraggable(aDraggable, rv); return rv.ErrorCode(); } - NS_IMETHOD GetContentEditable(nsAString& aContentEditable) MOZ_FINAL { + NS_IMETHOD GetContentEditable(nsAString& aContentEditable) + MOZ_FINAL MOZ_OVERRIDE { nsString contentEditable; GetContentEditable(contentEditable); aContentEditable.Assign(contentEditable); return NS_OK; } - NS_IMETHOD SetContentEditable(const nsAString& aContentEditable) MOZ_FINAL { + NS_IMETHOD SetContentEditable(const nsAString& aContentEditable) + MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetContentEditable(aContentEditable, rv); return rv.ErrorCode(); } - NS_IMETHOD GetIsContentEditable(bool* aIsContentEditable) MOZ_FINAL { + NS_IMETHOD GetIsContentEditable(bool* aIsContentEditable) + MOZ_FINAL MOZ_OVERRIDE { *aIsContentEditable = IsContentEditable(); return NS_OK; } - NS_IMETHOD GetContextMenu(nsIDOMHTMLMenuElement** aContextMenu) MOZ_FINAL; - NS_IMETHOD GetSpellcheck(bool* aSpellcheck) MOZ_FINAL { + NS_IMETHOD GetContextMenu(nsIDOMHTMLMenuElement** aContextMenu) + MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD GetSpellcheck(bool* aSpellcheck) MOZ_FINAL MOZ_OVERRIDE { *aSpellcheck = Spellcheck(); return NS_OK; } - NS_IMETHOD SetSpellcheck(bool aSpellcheck) MOZ_FINAL { + NS_IMETHOD SetSpellcheck(bool aSpellcheck) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetSpellcheck(aSpellcheck, rv); return rv.ErrorCode(); } - NS_IMETHOD GetOuterHTML(nsAString& aOuterHTML) MOZ_FINAL { + NS_IMETHOD GetOuterHTML(nsAString& aOuterHTML) MOZ_FINAL MOZ_OVERRIDE { mozilla::dom::Element::GetOuterHTML(aOuterHTML); return NS_OK; } - NS_IMETHOD SetOuterHTML(const nsAString& aOuterHTML) MOZ_FINAL { + NS_IMETHOD SetOuterHTML(const nsAString& aOuterHTML) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; mozilla::dom::Element::SetOuterHTML(aOuterHTML, rv); return rv.ErrorCode(); } \ NS_IMETHOD InsertAdjacentHTML(const nsAString& position, - const nsAString& text) MOZ_FINAL; - NS_IMETHOD ScrollIntoView(bool top, uint8_t _argc) MOZ_FINAL { + const nsAString& text) MOZ_FINAL MOZ_OVERRIDE; + NS_IMETHOD ScrollIntoView(bool top, uint8_t _argc) MOZ_FINAL MOZ_OVERRIDE { if (!_argc) { top = true; } mozilla::dom::Element::ScrollIntoView(top); return NS_OK; } - NS_IMETHOD GetOffsetParent(nsIDOMElement** aOffsetParent) MOZ_FINAL { + NS_IMETHOD GetOffsetParent(nsIDOMElement** aOffsetParent) + MOZ_FINAL MOZ_OVERRIDE { mozilla::dom::Element* offsetParent = GetOffsetParent(); if (!offsetParent) { *aOffsetParent = nullptr; @@ -480,41 +486,41 @@ public: } return CallQueryInterface(offsetParent, aOffsetParent); } - NS_IMETHOD GetOffsetTop(int32_t* aOffsetTop) MOZ_FINAL { + NS_IMETHOD GetOffsetTop(int32_t* aOffsetTop) MOZ_FINAL MOZ_OVERRIDE { *aOffsetTop = OffsetTop(); return NS_OK; } - NS_IMETHOD GetOffsetLeft(int32_t* aOffsetLeft) MOZ_FINAL { + NS_IMETHOD GetOffsetLeft(int32_t* aOffsetLeft) MOZ_FINAL MOZ_OVERRIDE { *aOffsetLeft = OffsetLeft(); return NS_OK; } - NS_IMETHOD GetOffsetWidth(int32_t* aOffsetWidth) MOZ_FINAL { + NS_IMETHOD GetOffsetWidth(int32_t* aOffsetWidth) MOZ_FINAL MOZ_OVERRIDE { *aOffsetWidth = OffsetWidth(); return NS_OK; } - NS_IMETHOD GetOffsetHeight(int32_t* aOffsetHeight) MOZ_FINAL { + NS_IMETHOD GetOffsetHeight(int32_t* aOffsetHeight) MOZ_FINAL MOZ_OVERRIDE { *aOffsetHeight = OffsetHeight(); return NS_OK; } - NS_IMETHOD DOMClick() MOZ_FINAL { + NS_IMETHOD DOMClick() MOZ_FINAL MOZ_OVERRIDE { Click(); return NS_OK; } - NS_IMETHOD GetTabIndex(int32_t* aTabIndex) MOZ_FINAL { + NS_IMETHOD GetTabIndex(int32_t* aTabIndex) MOZ_FINAL MOZ_OVERRIDE { *aTabIndex = TabIndex(); return NS_OK; } - NS_IMETHOD SetTabIndex(int32_t aTabIndex) MOZ_FINAL { + NS_IMETHOD SetTabIndex(int32_t aTabIndex) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetTabIndex(aTabIndex, rv); return rv.ErrorCode(); } - NS_IMETHOD Focus() MOZ_FINAL { + NS_IMETHOD Focus() MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; Focus(rv); return rv.ErrorCode(); } - NS_IMETHOD GetDraggable(bool* aDraggable) MOZ_FINAL { + NS_IMETHOD GetDraggable(bool* aDraggable) MOZ_FINAL MOZ_OVERRIDE { *aDraggable = Draggable(); return NS_OK; } @@ -522,7 +528,7 @@ public: return mozilla::dom::Element::GetInnerHTML(aInnerHTML); } using mozilla::dom::Element::SetInnerHTML; - NS_IMETHOD SetInnerHTML(const nsAString& aInnerHTML) MOZ_FINAL { + NS_IMETHOD SetInnerHTML(const nsAString& aInnerHTML) MOZ_FINAL MOZ_OVERRIDE { mozilla::ErrorResult rv; SetInnerHTML(aInnerHTML, rv); return rv.ErrorCode(); diff --git a/dom/media/fmp4/MP4Reader.cpp b/dom/media/fmp4/MP4Reader.cpp index 66ffa3e724e..37e62641063 100644 --- a/dom/media/fmp4/MP4Reader.cpp +++ b/dom/media/fmp4/MP4Reader.cpp @@ -107,7 +107,6 @@ InvokeAndRetry(ThisType* aThisVal, ReturnType(ThisType::*aMethod)(), MP4Stream* } } - MP4Reader::MP4Reader(AbstractMediaDecoder* aDecoder) : MediaDecoderReader(aDecoder) , mAudio(MediaData::AUDIO_DATA, Preferences::GetUint("media.mp4-audio-decode-ahead", 2)) @@ -196,6 +195,7 @@ MP4Reader::InitLayersBackendType() } static bool sIsEMEEnabled = false; +static bool sDemuxSkipToNextKeyframe = true; nsresult MP4Reader::Init(MediaDecoderReader* aCloneDonor) @@ -217,6 +217,7 @@ MP4Reader::Init(MediaDecoderReader* aCloneDonor) if (!sSetupPrefCache) { sSetupPrefCache = true; Preferences::AddBoolVarCache(&sIsEMEEnabled, "media.eme.enabled", false); + Preferences::AddBoolVarCache(&sDemuxSkipToNextKeyframe, "media.fmp4.demux-skip", true); } return NS_OK; @@ -519,6 +520,29 @@ MP4Reader::GetDecoderData(TrackType aTrack) return mVideo; } +Microseconds +MP4Reader::GetNextKeyframeTime() +{ + MonitorAutoLock mon(mDemuxerMonitor); + return mDemuxer->GetNextKeyframeTime(); +} + +bool +MP4Reader::ShouldSkip(bool aSkipToNextKeyframe, int64_t aTimeThreshold) +{ + // The MP4Reader doesn't do normal skip-to-next-keyframe if the demuxer + // has exposes where the next keyframe is. We can then instead skip only + // if the time threshold (the current playback position) is after the next + // keyframe in the stream. This means we'll only skip frames that we have + // no hope of ever playing. + Microseconds nextKeyframe = -1; + if (!sDemuxSkipToNextKeyframe || + (nextKeyframe = GetNextKeyframeTime()) == -1) { + return aSkipToNextKeyframe; + } + return nextKeyframe < aTimeThreshold; +} + nsRefPtr MP4Reader::RequestVideoData(bool aSkipToNextKeyframe, int64_t aTimeThreshold) @@ -537,7 +561,7 @@ MP4Reader::RequestVideoData(bool aSkipToNextKeyframe, MOZ_ASSERT(HasVideo() && mPlatform && mVideo.mDecoder); bool eos = false; - if (aSkipToNextKeyframe) { + if (ShouldSkip(aSkipToNextKeyframe, aTimeThreshold)) { uint32_t parsed = 0; eos = !SkipVideoDemuxToNextKeyFrame(aTimeThreshold, parsed); if (!eos && NS_FAILED(mVideo.mDecoder->Flush())) { diff --git a/dom/media/fmp4/MP4Reader.h b/dom/media/fmp4/MP4Reader.h index 67ca44c91c5..626988aaa77 100644 --- a/dom/media/fmp4/MP4Reader.h +++ b/dom/media/fmp4/MP4Reader.h @@ -121,6 +121,9 @@ private: bool IsWaitingOnCodecResource(); virtual bool IsWaitingOnCDMResource() MOZ_OVERRIDE; + Microseconds GetNextKeyframeTime(); + bool ShouldSkip(bool aSkipToNextKeyframe, int64_t aTimeThreshold); + size_t SizeOfQueue(TrackType aTrack); nsRefPtr mStream; diff --git a/dom/media/fmp4/apple/AppleVDADecoder.cpp b/dom/media/fmp4/apple/AppleVDADecoder.cpp index 74958c489c5..08bfa063094 100644 --- a/dom/media/fmp4/apple/AppleVDADecoder.cpp +++ b/dom/media/fmp4/apple/AppleVDADecoder.cpp @@ -356,10 +356,6 @@ AppleVDADecoder::SubmitFrame(mp4_demuxer::MP4Sample* aSample) block, frameInfo); - LOG("[%s]: FrameInfo retain count = %ld", - __func__, CFGetRetainCount(frameInfo)); - MOZ_ASSERT(CFGetRetainCount(frameInfo) >= 2, "Bad retain count"); - if (rv != noErr) { NS_WARNING("AppleVDADecoder: Couldn't pass frame to decoder"); return NS_ERROR_FAILURE; diff --git a/dom/media/fmp4/wmf/MFTDecoder.cpp b/dom/media/fmp4/wmf/MFTDecoder.cpp index e2b74049c6b..082afe4cb00 100644 --- a/dom/media/fmp4/wmf/MFTDecoder.cpp +++ b/dom/media/fmp4/wmf/MFTDecoder.cpp @@ -48,9 +48,9 @@ MFTDecoder::Create(const GUID& aMFTClsID) HRESULT MFTDecoder::SetMediaTypes(IMFMediaType* aInputType, - const GUID& aOutputSubType) + IMFMediaType* aOutputType) { - mOutputSubtype = aOutputSubType; + mOutputType = aOutputType; // Set the input type to the one the caller gave us... HRESULT hr = mDecoder->SetInputType(0, aInputType, 0); @@ -96,21 +96,14 @@ MFTDecoder::SetDecoderOutputType() RefPtr outputType; UINT32 typeIndex = 0; while (SUCCEEDED(mDecoder->GetOutputAvailableType(0, typeIndex++, byRef(outputType)))) { - GUID subtype; - hr = outputType->GetGUID(MF_MT_SUBTYPE, &subtype); - if (FAILED(hr)) { - continue; - } - if (subtype == mOutputSubtype) { - if (subtype == MFAudioFormat_PCM) { - // Set output to PCM 16 bits, we can ignore errors. - outputType->SetUINT32(MF_MT_SAMPLE_SIZE, 2); - outputType->SetUINT32(MF_MT_AUDIO_BITS_PER_SAMPLE, 16); - } + BOOL resultMatch; + hr = mOutputType->Compare(outputType, MF_ATTRIBUTES_MATCH_OUR_ITEMS, &resultMatch); + if (SUCCEEDED(hr) && resultMatch == TRUE) { hr = mDecoder->SetOutputType(0, outputType, 0); NS_ENSURE_TRUE(SUCCEEDED(hr), hr); return S_OK; } + outputType = nullptr; } return E_FAIL; } diff --git a/dom/media/fmp4/wmf/MFTDecoder.h b/dom/media/fmp4/wmf/MFTDecoder.h index b397dc25cc9..45d6a90572a 100644 --- a/dom/media/fmp4/wmf/MFTDecoder.h +++ b/dom/media/fmp4/wmf/MFTDecoder.h @@ -33,11 +33,11 @@ public: // // Params: // - aInputType needs at least major and minor types set. - // - aOutputSubType is the minor type of the same major type e.g. - // MFVideoFormat_H264. This is used to select the output type out + // - aOutputType needs at least major and minor types set. + // This is used to select the matching output type out // of all the available output types of the MFT. HRESULT SetMediaTypes(IMFMediaType* aInputType, - const GUID& aOutputSubType); + IMFMediaType* aOutputType); // Returns the MFT's IMFAttributes object. TemporaryRef GetAttributes(); @@ -92,7 +92,7 @@ private: RefPtr mDecoder; - GUID mOutputSubtype; + RefPtr mOutputType; // True if the IMFTransform allocates the samples that it returns. bool mMFTProvidesOutputSamples; diff --git a/dom/media/fmp4/wmf/WMFAudioMFTManager.cpp b/dom/media/fmp4/wmf/WMFAudioMFTManager.cpp index f039b866822..2e0acb3c713 100644 --- a/dom/media/fmp4/wmf/WMFAudioMFTManager.cpp +++ b/dom/media/fmp4/wmf/WMFAudioMFTManager.cpp @@ -128,34 +128,47 @@ WMFAudioMFTManager::Init() NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); // Setup input/output media types - RefPtr type; + RefPtr inputType; - hr = wmf::MFCreateMediaType(byRef(type)); + hr = wmf::MFCreateMediaType(byRef(inputType)); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Audio); + hr = inputType->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Audio); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetGUID(MF_MT_SUBTYPE, GetMediaSubtypeGUID()); + hr = inputType->SetGUID(MF_MT_SUBTYPE, GetMediaSubtypeGUID()); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetUINT32(MF_MT_AUDIO_SAMPLES_PER_SECOND, mAudioRate); + hr = inputType->SetUINT32(MF_MT_AUDIO_SAMPLES_PER_SECOND, mAudioRate); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetUINT32(MF_MT_AUDIO_NUM_CHANNELS, mAudioChannels); + hr = inputType->SetUINT32(MF_MT_AUDIO_NUM_CHANNELS, mAudioChannels); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); if (mStreamType == AAC) { - hr = type->SetUINT32(MF_MT_AAC_PAYLOAD_TYPE, 0x0); // Raw AAC packet + hr = inputType->SetUINT32(MF_MT_AAC_PAYLOAD_TYPE, 0x0); // Raw AAC packet NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetBlob(MF_MT_USER_DATA, - mUserData.Elements(), - mUserData.Length()); + hr = inputType->SetBlob(MF_MT_USER_DATA, + mUserData.Elements(), + mUserData.Length()); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); } - hr = decoder->SetMediaTypes(type, MFAudioFormat_PCM); + RefPtr outputType; + hr = wmf::MFCreateMediaType(byRef(outputType)); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + hr = outputType->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Audio); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + hr = outputType->SetGUID(MF_MT_SUBTYPE, MFAudioFormat_PCM); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + hr = outputType->SetUINT32(MF_MT_AUDIO_BITS_PER_SAMPLE, 16); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + hr = decoder->SetMediaTypes(inputType, outputType); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); mDecoder = decoder; diff --git a/dom/media/fmp4/wmf/WMFVideoMFTManager.cpp b/dom/media/fmp4/wmf/WMFVideoMFTManager.cpp index 039f6ba98e2..48d60fad7d1 100644 --- a/dom/media/fmp4/wmf/WMFVideoMFTManager.cpp +++ b/dom/media/fmp4/wmf/WMFVideoMFTManager.cpp @@ -188,21 +188,31 @@ WMFVideoMFTManager::Init() } // Setup the input/output media types. - RefPtr type; - hr = wmf::MFCreateMediaType(byRef(type)); + RefPtr inputType; + hr = wmf::MFCreateMediaType(byRef(inputType)); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Video); + hr = inputType->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Video); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetGUID(MF_MT_SUBTYPE, GetMediaSubtypeGUID()); + hr = inputType->SetGUID(MF_MT_SUBTYPE, GetMediaSubtypeGUID()); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - hr = type->SetUINT32(MF_MT_INTERLACE_MODE, MFVideoInterlace_MixedInterlaceOrProgressive); + hr = inputType->SetUINT32(MF_MT_INTERLACE_MODE, MFVideoInterlace_MixedInterlaceOrProgressive); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); - GUID outputType = mUseHwAccel ? MFVideoFormat_NV12 : MFVideoFormat_YV12; - hr = decoder->SetMediaTypes(type, outputType); + RefPtr outputType; + hr = wmf::MFCreateMediaType(byRef(outputType)); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + hr = outputType->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Video); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + GUID outputSubType = mUseHwAccel ? MFVideoFormat_NV12 : MFVideoFormat_YV12; + hr = outputType->SetGUID(MF_MT_SUBTYPE, outputSubType); + NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); + + hr = decoder->SetMediaTypes(inputType, outputType); NS_ENSURE_TRUE(SUCCEEDED(hr), nullptr); mDecoder = decoder; diff --git a/dom/plugins/base/nsJSNPRuntime.cpp b/dom/plugins/base/nsJSNPRuntime.cpp index cd08f7dbc80..c4c5186f3da 100644 --- a/dom/plugins/base/nsJSNPRuntime.cpp +++ b/dom/plugins/base/nsJSNPRuntime.cpp @@ -402,7 +402,7 @@ DestroyJSObjWrapperTable() static bool CreateNPObjWrapperTable() { - MOZ_ASSERT(!sNPObjWrappers.ops); + MOZ_ASSERT(!sNPObjWrappers.IsInitialized()); if (!RegisterGCCallbacks()) { return false; @@ -419,8 +419,6 @@ DestroyNPObjWrapperTable() MOZ_ASSERT(sNPObjWrappers.EntryCount() == 0); PL_DHashTableFinish(&sNPObjWrappers); - - sNPObjWrappers.ops = nullptr; } static void @@ -439,7 +437,7 @@ OnWrapperDestroyed() DestroyJSObjWrapperTable(); } - if (sNPObjWrappers.ops) { + if (sNPObjWrappers.IsInitialized()) { // No more wrappers, and our hash was initialized. Finish the // hash to prevent leaking it. DestroyNPObjWrapperTable(); @@ -1749,7 +1747,7 @@ NPObjWrapper_Finalize(js::FreeOp *fop, JSObject *obj) { NPObject *npobj = (NPObject *)::JS_GetPrivate(obj); if (npobj) { - if (sNPObjWrappers.ops) { + if (sNPObjWrappers.IsInitialized()) { PL_DHashTableRemove(&sNPObjWrappers, npobj); } } @@ -1765,7 +1763,7 @@ NPObjWrapper_ObjectMoved(JSObject *obj, const JSObject *old) // The wrapper JSObject has been moved, so we need to update the entry in the // sNPObjWrappers hash table, if present. - if (!sNPObjWrappers.ops) { + if (!sNPObjWrappers.IsInitialized()) { return; } @@ -1824,7 +1822,7 @@ nsNPObjWrapper::OnDestroy(NPObject *npobj) return; } - if (!sNPObjWrappers.ops) { + if (!sNPObjWrappers.IsInitialized()) { // No hash yet (or any more), no used wrappers available. return; @@ -1874,7 +1872,7 @@ nsNPObjWrapper::GetNewOrUsed(NPP npp, JSContext *cx, NPObject *npobj) return nullptr; } - if (!sNPObjWrappers.ops) { + if (!sNPObjWrappers.IsInitialized()) { // No hash yet (or any more), initialize it. if (!CreateNPObjWrapperTable()) { return nullptr; @@ -1960,8 +1958,8 @@ NPObjWrapperPluginDestroyedCallback(PLDHashTable *table, PLDHashEntryHdr *hdr, if (entry->mNpp == nppcx->npp) { // Prevent invalidate() and deallocate() from touching the hash // we're enumerating. - const PLDHashTableOps *ops = table->ops; - table->ops = nullptr; + const PLDHashTableOps *ops = table->Ops(); + table->SetOps(nullptr); NPObject *npobj = entry->mNPObj; @@ -1989,7 +1987,7 @@ NPObjWrapperPluginDestroyedCallback(PLDHashTable *table, PLDHashEntryHdr *hdr, ::JS_SetPrivate(entry->mJSObj, nullptr); - table->ops = ops; + table->SetOps(ops); if (sDelayedReleases && sDelayedReleases->RemoveElement(npobj)) { OnWrapperDestroyed(); @@ -2030,7 +2028,7 @@ nsJSNPRuntime::OnPluginDestroy(NPP npp) // Use the safe JSContext here as we're not always able to find the // JSContext associated with the NPP any more. AutoSafeJSContext cx; - if (sNPObjWrappers.ops) { + if (sNPObjWrappers.IsInitialized()) { NppAndCx nppcx = { npp, cx }; PL_DHashTableEnumerate(&sNPObjWrappers, NPObjWrapperPluginDestroyedCallback, &nppcx); diff --git a/dom/xul/templates/nsContentSupportMap.cpp b/dom/xul/templates/nsContentSupportMap.cpp index 25fa5cf7263..00d5d51aed6 100644 --- a/dom/xul/templates/nsContentSupportMap.cpp +++ b/dom/xul/templates/nsContentSupportMap.cpp @@ -15,14 +15,14 @@ nsContentSupportMap::Init() void nsContentSupportMap::Finish() { - if (mMap.ops) + if (mMap.IsInitialized()) PL_DHashTableFinish(&mMap); } nsresult nsContentSupportMap::Remove(nsIContent* aElement) { - if (!mMap.ops) + if (!mMap.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; nsIContent* child = aElement; diff --git a/dom/xul/templates/nsContentSupportMap.h b/dom/xul/templates/nsContentSupportMap.h index c64c1a6190d..216aab57d11 100644 --- a/dom/xul/templates/nsContentSupportMap.h +++ b/dom/xul/templates/nsContentSupportMap.h @@ -25,7 +25,7 @@ public: ~nsContentSupportMap() { Finish(); } nsresult Put(nsIContent* aElement, nsTemplateMatch* aMatch) { - if (!mMap.ops) + if (!mMap.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; PLDHashEntryHdr* hdr = PL_DHashTableAdd(&mMap, aElement); @@ -39,7 +39,7 @@ public: return NS_OK; } bool Get(nsIContent* aElement, nsTemplateMatch** aMatch) { - if (!mMap.ops) + if (!mMap.IsInitialized()) return false; PLDHashEntryHdr* hdr = PL_DHashTableLookup(&mMap, aElement); diff --git a/gfx/2d/DrawTargetD2D1.cpp b/gfx/2d/DrawTargetD2D1.cpp index 64110e4cb10..484a5b7a1fc 100644 --- a/gfx/2d/DrawTargetD2D1.cpp +++ b/gfx/2d/DrawTargetD2D1.cpp @@ -859,7 +859,12 @@ DrawTargetD2D1::factory() return mFactory; } - HRESULT hr = D2DFactory()->QueryInterface((ID2D1Factory1**)&mFactory); + ID2D1Factory* d2dFactory = D2DFactory(); + if (!d2dFactory) { + return nullptr; + } + + HRESULT hr = d2dFactory->QueryInterface((ID2D1Factory1**)&mFactory); if (FAILED(hr)) { return nullptr; diff --git a/gfx/layers/apz/src/APZCTreeManager.cpp b/gfx/layers/apz/src/APZCTreeManager.cpp index 43f0ca86949..fd137cec9b0 100644 --- a/gfx/layers/apz/src/APZCTreeManager.cpp +++ b/gfx/layers/apz/src/APZCTreeManager.cpp @@ -649,9 +649,6 @@ APZCTreeManager::ReceiveInputEvent(InputData& aEvent, break; } } - if (hitResult == HitOverscrolledApzc) { - result = nsEventStatus_eConsumeNoDefault; - } return result; } @@ -772,9 +769,6 @@ APZCTreeManager::ProcessTouchInput(MultiTouchInput& aInput, outTransform, touchData.mScreenPoint); } } - if (mHitResultForInputBlock == HitOverscrolledApzc) { - result = nsEventStatus_eConsumeNoDefault; - } if (aInput.mType == MultiTouchInput::MULTITOUCH_END) { if (mTouchCount >= aInput.mTouches.Length()) { @@ -834,9 +828,6 @@ APZCTreeManager::ProcessEvent(WidgetInputEvent& aEvent, Matrix4x4 outTransform = transformToApzc * transformToGecko; aEvent.refPoint = TransformTo(outTransform, aEvent.refPoint); } - if (hitResult == HitOverscrolledApzc) { - result = nsEventStatus_eConsumeNoDefault; - } return result; } @@ -1195,8 +1186,6 @@ APZCTreeManager::GetTargetAPZC(const ScreenPoint& aPoint, HitTestResult* aOutHit PixelCastJustification::ScreenIsParentLayerForRoot); nsRefPtr target = GetAPZCAtPoint(mRootNode, point, &hitResult); - // If we are in an overscrolled APZC, we should be returning nullptr. - MOZ_ASSERT(!(target && (hitResult == HitOverscrolledApzc))); if (aOutHitResult) { *aOutHitResult = hitResult; } @@ -1322,8 +1311,6 @@ APZCTreeManager::GetAPZCAtPoint(HitTestingTreeNode* aNode, // This walks the tree in depth-first, reverse order, so that it encounters // APZCs front-to-back on the screen. for (HitTestingTreeNode* node = aNode; node; node = node->GetPrevSibling()) { - AsyncPanZoomController* apzc = node->GetApzc(); - if (node->IsOutsideClip(aHitTestPoint)) { // If the point being tested is outside the clip region for this node // then we don't need to test against this node or any of its children. @@ -1342,10 +1329,6 @@ APZCTreeManager::GetAPZCAtPoint(HitTestingTreeNode* aNode, ParentLayerPoint childPoint = ViewAs(hitTestPointForChildLayers.ref(), PixelCastJustification::MovingDownToChildren); result = GetAPZCAtPoint(node->GetLastChild(), childPoint, aOutHitResult); - if (*aOutHitResult == HitOverscrolledApzc) { - // We matched an overscrolled APZC, abort. - return nullptr; - } } // If we didn't match anything in the subtree, check |node|. @@ -1365,15 +1348,6 @@ APZCTreeManager::GetAPZCAtPoint(HitTestingTreeNode* aNode, } } - // If we are overscrolled, and the point matches us or one of our children, - // the result is inside an overscrolled APZC, inform our caller of this - // (callers typically ignore events targeted at overscrolled APZCs). - if (*aOutHitResult != HitNothing && apzc && apzc->IsOverscrolled()) { - APZCTM_LOG("Result is inside overscrolled APZC %p\n", apzc); - *aOutHitResult = HitOverscrolledApzc; - return nullptr; - } - if (*aOutHitResult != HitNothing) { if (result && !gfxPrefs::LayoutEventRegionsEnabled()) { // When event-regions are disabled, we treat scrollinfo layers as @@ -1523,7 +1497,7 @@ APZCTreeManager::GetScreenToApzcTransform(const AsyncPanZoomController *aApzc) c // ancestorUntransform is updated to RC.Inverse() * QC.Inverse() when parent == P ancestorUntransform = parent->GetAncestorTransform().Inverse(); // asyncUntransform is updated to PA.Inverse() when parent == P - Matrix4x4 asyncUntransform = Matrix4x4(parent->GetCurrentAsyncTransform()).Inverse(); + Matrix4x4 asyncUntransform = parent->GetCurrentAsyncTransformWithOverscroll().Inverse(); // untransformSinceLastApzc is RC.Inverse() * QC.Inverse() * PA.Inverse() Matrix4x4 untransformSinceLastApzc = ancestorUntransform * asyncUntransform; @@ -1555,7 +1529,7 @@ APZCTreeManager::GetApzcToGeckoTransform(const AsyncPanZoomController *aApzc) co // leftmost matrix in a multiplication is applied first. // asyncUntransform is LA.Inverse() - Matrix4x4 asyncUntransform = Matrix4x4(aApzc->GetCurrentAsyncTransform()).Inverse(); + Matrix4x4 asyncUntransform = aApzc->GetCurrentAsyncTransformWithOverscroll().Inverse(); // aTransformToGeckoOut is initialized to LA.Inverse() * LD * MC * NC * OC * PC result = asyncUntransform * aApzc->GetTransformToLastDispatchedPaint() * aApzc->GetAncestorTransform(); diff --git a/gfx/layers/apz/src/APZUtils.h b/gfx/layers/apz/src/APZUtils.h index b60347d549c..ec142d75bdc 100644 --- a/gfx/layers/apz/src/APZUtils.h +++ b/gfx/layers/apz/src/APZUtils.h @@ -14,7 +14,11 @@ enum HitTestResult { HitNothing, HitLayer, HitDispatchToContentRegion, - HitOverscrolledApzc, +}; + +enum CancelAnimationFlags : uint32_t { + Default = 0, /* Cancel all animations */ + ExcludeOverscroll = 1 /* Don't clear overscroll */ }; } diff --git a/gfx/layers/apz/src/AsyncPanZoomController.cpp b/gfx/layers/apz/src/AsyncPanZoomController.cpp index fb28129b4cf..dd64c7c0b50 100644 --- a/gfx/layers/apz/src/AsyncPanZoomController.cpp +++ b/gfx/layers/apz/src/AsyncPanZoomController.cpp @@ -1146,7 +1146,8 @@ nsEventStatus AsyncPanZoomController::OnTouchStart(const MultiTouchInput& aEvent case FLING: case ANIMATING_ZOOM: case SMOOTH_SCROLL: - CurrentTouchBlock()->GetOverscrollHandoffChain()->CancelAnimations(); + case OVERSCROLL_ANIMATION: + CurrentTouchBlock()->GetOverscrollHandoffChain()->CancelAnimations(ExcludeOverscroll); // Fall through. case NOTHING: { mX.StartTouch(point.x, aEvent.mTime); @@ -1226,8 +1227,8 @@ nsEventStatus AsyncPanZoomController::OnTouchMove(const MultiTouchInput& aEvent) case OVERSCROLL_ANIMATION: // Should not receive a touch-move in the OVERSCROLL_ANIMATION state - // as touch blocks that begin in an overscrolled state - // are ignored. + // as touch blocks that begin in an overscrolled state cancel the + // animation. NS_WARNING("Received impossible touch in OnTouchMove"); break; } @@ -1269,7 +1270,11 @@ nsEventStatus AsyncPanZoomController::OnTouchEnd(const MultiTouchInput& aEvent) // that were not big enough to trigger scrolling. Clear that out. mX.SetVelocity(0); mY.SetVelocity(0); - SetState(NOTHING); + // It's possible we may be overscrolled if the user tapped during a + // previous overscroll pan. Make sure to snap back in this situation. + if (!SnapBackIfOverscrolled()) { + SetState(NOTHING); + } return nsEventStatus_eIgnore; case PANNING: @@ -1310,9 +1315,9 @@ nsEventStatus AsyncPanZoomController::OnTouchEnd(const MultiTouchInput& aEvent) return nsEventStatus_eIgnore; case OVERSCROLL_ANIMATION: - // Should not receive a touch-move in the OVERSCROLL_ANIMATION state - // as touch blocks that begin in an overscrolled state - // are ignored. + // Should not receive a touch-end in the OVERSCROLL_ANIMATION state + // as touch blocks that begin in an overscrolled state cancel the + // animation. NS_WARNING("Received impossible touch in OnTouchEnd"); break; } @@ -2164,7 +2169,7 @@ void AsyncPanZoomController::StartAnimation(AsyncPanZoomAnimation* aAnimation) ScheduleComposite(); } -void AsyncPanZoomController::CancelAnimation() { +void AsyncPanZoomController::CancelAnimation(CancelAnimationFlags aFlags) { ReentrantMonitorAutoEnter lock(mMonitor); APZC_LOG("%p running CancelAnimation in state %d\n", this, mState); SetState(NOTHING); @@ -2176,7 +2181,7 @@ void AsyncPanZoomController::CancelAnimation() { // Setting the state to nothing and cancelling the animation can // preempt normal mechanisms for relieving overscroll, so we need to clear // overscroll here. - if (mX.IsOverscrolled() || mY.IsOverscrolled()) { + if (!(aFlags & ExcludeOverscroll) && IsOverscrolled()) { ClearOverscroll(); RequestContentRepaint(); ScheduleComposite(); @@ -2653,6 +2658,10 @@ ViewTransform AsyncPanZoomController::GetCurrentAsyncTransform() const { return ViewTransform(mFrameMetrics.GetAsyncZoom(), -translation); } +Matrix4x4 AsyncPanZoomController::GetCurrentAsyncTransformWithOverscroll() const { + return Matrix4x4(GetCurrentAsyncTransform()) * GetOverscrollTransform(); +} + Matrix4x4 AsyncPanZoomController::GetTransformToLastDispatchedPaint() const { ReentrantMonitorAutoEnter lock(mMonitor); diff --git a/gfx/layers/apz/src/AsyncPanZoomController.h b/gfx/layers/apz/src/AsyncPanZoomController.h index c6162688d64..ccacbf67b6d 100644 --- a/gfx/layers/apz/src/AsyncPanZoomController.h +++ b/gfx/layers/apz/src/AsyncPanZoomController.h @@ -20,6 +20,7 @@ #include "InputData.h" #include "Axis.h" #include "InputQueue.h" +#include "APZUtils.h" #include "LayersTypes.h" #include "TaskThrottler.h" #include "mozilla/gfx/Matrix.h" @@ -217,6 +218,12 @@ public: */ ViewTransform GetCurrentAsyncTransform() const; + /** + * Returns the same transform as GetCurrentAsyncTransform(), but includes + * any transform due to axis over-scroll. + */ + Matrix4x4 GetCurrentAsyncTransformWithOverscroll() const; + /** * Returns the transform to take something from the coordinate space of the * last thing we know gecko painted, to the coordinate space of the last thing @@ -285,8 +292,10 @@ public: /** * Cancels any currently running animation. + * aFlags is a bit-field to provide specifics of how to cancel the animation. + * See CancelAnimationFlags. */ - void CancelAnimation(); + void CancelAnimation(CancelAnimationFlags aFlags = Default); /** * Clear any overscroll on this APZC. diff --git a/gfx/layers/apz/src/Axis.cpp b/gfx/layers/apz/src/Axis.cpp index b5ef2065f6c..a88207ca036 100644 --- a/gfx/layers/apz/src/Axis.cpp +++ b/gfx/layers/apz/src/Axis.cpp @@ -126,6 +126,8 @@ bool Axis::AdjustDisplacement(ParentLayerCoord aDisplacement, return false; } + StopSamplingOverscrollAnimation(); + ParentLayerCoord displacement = aDisplacement; // First consume any overscroll in the opposite direction along this axis. @@ -160,12 +162,13 @@ ParentLayerCoord Axis::ApplyResistance(ParentLayerCoord aRequestedOverscroll) co // The actual overscroll is the requested overscroll multiplied by this // factor; this should prevent overscrolling by more than the composition // length. - float resistanceFactor = 1 - fabsf(mOverscroll) / GetCompositionLength(); + float resistanceFactor = 1 - fabsf(GetOverscroll()) / GetCompositionLength(); return resistanceFactor < 0 ? ParentLayerCoord(0) : aRequestedOverscroll * resistanceFactor; } void Axis::OverscrollBy(ParentLayerCoord aOverscroll) { MOZ_ASSERT(CanScroll()); + StopSamplingOverscrollAnimation(); aOverscroll = ApplyResistance(aOverscroll); if (aOverscroll > 0) { #ifdef DEBUG @@ -200,6 +203,12 @@ ParentLayerCoord Axis::GetOverscroll() const { return result; } +void Axis::StopSamplingOverscrollAnimation() { + ParentLayerCoord overscroll = GetOverscroll(); + ClearOverscroll(); + mOverscroll = overscroll; +} + void Axis::StepOverscrollAnimation(double aStepDurationMilliseconds) { // Apply spring physics to the overscroll as time goes on. // Note: this method of sampling isn't perfectly smooth, as it assumes diff --git a/gfx/layers/apz/src/Axis.h b/gfx/layers/apz/src/Axis.h index 4f24262139d..f325034a2c4 100644 --- a/gfx/layers/apz/src/Axis.h +++ b/gfx/layers/apz/src/Axis.h @@ -251,6 +251,10 @@ protected: // actual overscroll amount. ParentLayerCoord ApplyResistance(ParentLayerCoord aOverscroll) const; + // Helper function to disable overscroll transformations triggered by + // SampleOverscrollAnimation(). + void StopSamplingOverscrollAnimation(); + // Helper function for SampleOverscrollAnimation(). void StepOverscrollAnimation(double aStepDurationMilliseconds); diff --git a/gfx/layers/apz/src/HitTestingTreeNode.cpp b/gfx/layers/apz/src/HitTestingTreeNode.cpp index 0e7bb1b6b9f..9f43a06d9c4 100644 --- a/gfx/layers/apz/src/HitTestingTreeNode.cpp +++ b/gfx/layers/apz/src/HitTestingTreeNode.cpp @@ -174,7 +174,7 @@ HitTestingTreeNode::Untransform(const ParentLayerPoint& aPoint) const // convert into Layer coordinate space gfx::Matrix4x4 localTransform = mTransform; if (mApzc) { - localTransform = localTransform * gfx::Matrix4x4(mApzc->GetCurrentAsyncTransform()); + localTransform = localTransform * mApzc->GetCurrentAsyncTransformWithOverscroll(); } gfx::Point4D point = localTransform.Inverse().ProjectPoint(aPoint.ToUnknownPoint()); return point.HasPositiveWCoord() diff --git a/gfx/layers/apz/src/InputQueue.cpp b/gfx/layers/apz/src/InputQueue.cpp index d5ee9c8a28d..5ecdf47d5d8 100644 --- a/gfx/layers/apz/src/InputQueue.cpp +++ b/gfx/layers/apz/src/InputQueue.cpp @@ -186,7 +186,7 @@ InputQueue::CancelAnimationsForNewBlock(CancelableBlockState* aBlock) INPQ_LOG("block %p tagged as fast-motion\n", touch); } } - aBlock->GetOverscrollHandoffChain()->CancelAnimations(); + aBlock->GetOverscrollHandoffChain()->CancelAnimations(ExcludeOverscroll); } } diff --git a/gfx/layers/apz/src/OverscrollHandoffState.cpp b/gfx/layers/apz/src/OverscrollHandoffState.cpp index b3e8cc04a18..36ffb255e06 100644 --- a/gfx/layers/apz/src/OverscrollHandoffState.cpp +++ b/gfx/layers/apz/src/OverscrollHandoffState.cpp @@ -88,9 +88,12 @@ OverscrollHandoffChain::FlushRepaints() const } void -OverscrollHandoffChain::CancelAnimations() const +OverscrollHandoffChain::CancelAnimations(CancelAnimationFlags aFlags) const { - ForEachApzc(&AsyncPanZoomController::CancelAnimation); + MOZ_ASSERT(Length() > 0); + for (uint32_t i = 0; i < Length(); ++i) { + mChain[i]->CancelAnimation(aFlags); + } } void diff --git a/gfx/layers/apz/src/OverscrollHandoffState.h b/gfx/layers/apz/src/OverscrollHandoffState.h index 60d45f73ca4..a5b0200f779 100644 --- a/gfx/layers/apz/src/OverscrollHandoffState.h +++ b/gfx/layers/apz/src/OverscrollHandoffState.h @@ -11,6 +11,7 @@ #include "nsAutoPtr.h" #include "nsISupportsImpl.h" // for NS_INLINE_DECL_REFCOUNTING #include "Units.h" // for ScreenPoint +#include "APZUtils.h" // for CancelAnimationFlags namespace mozilla { namespace layers { @@ -93,7 +94,7 @@ public: void FlushRepaints() const; // Cancel animations all the way up the chain. - void CancelAnimations() const; + void CancelAnimations(CancelAnimationFlags aFlags = Default) const; // Clear overscroll all the way up the chain. void ClearOverscroll() const; diff --git a/gfx/thebes/gfxASurface.h b/gfx/thebes/gfxASurface.h index 4cefa659fa5..a9ad7588e8e 100644 --- a/gfx/thebes/gfxASurface.h +++ b/gfx/thebes/gfxASurface.h @@ -229,7 +229,7 @@ public: } virtual ~gfxUnknownSurface() { } - virtual const nsIntSize GetSize() const { return mSize; } + virtual const nsIntSize GetSize() const MOZ_OVERRIDE { return mSize; } private: nsIntSize mSize; diff --git a/gfx/thebes/gfxFT2FontList.cpp b/gfx/thebes/gfxFT2FontList.cpp index 7bf8cd99809..98d6b5fe621 100644 --- a/gfx/thebes/gfxFT2FontList.cpp +++ b/gfx/thebes/gfxFT2FontList.cpp @@ -640,7 +640,7 @@ public: ~FontNameCache() { - if (!mMap.ops) { + if (!mMap.IsInitialized()) { return; } if (!mWriteNeeded || !mCache) { @@ -656,7 +656,7 @@ public: void Init() { - if (!mMap.ops || !mCache) { + if (!mMap.IsInitialized() || !mCache) { return; } uint32_t size; @@ -712,7 +712,7 @@ public: GetInfoForFile(const nsCString& aFileName, nsCString& aFaceList, uint32_t *aTimestamp, uint32_t *aFilesize) { - if (!mMap.ops) { + if (!mMap.IsInitialized()) { return; } PLDHashEntryHdr *hdr = @@ -736,7 +736,7 @@ public: CacheFileInfo(const nsCString& aFileName, const nsCString& aFaceList, uint32_t aTimestamp, uint32_t aFilesize) { - if (!mMap.ops) { + if (!mMap.IsInitialized()) { return; } FNCMapEntry* entry = diff --git a/gfx/thebes/gfxFont.h b/gfx/thebes/gfxFont.h index 7443d517a90..dbb535ef0f6 100644 --- a/gfx/thebes/gfxFont.h +++ b/gfx/thebes/gfxFont.h @@ -312,7 +312,7 @@ public: // This gets called when the timeout has expired on a zero-refcount // font; we just delete it. - virtual void NotifyExpired(gfxFont *aFont); + virtual void NotifyExpired(gfxFont *aFont) MOZ_OVERRIDE; // Cleans out the hashtable and removes expired fonts waiting for cleanup. // Other gfxFont objects may be still in use but they will be pushed @@ -1197,7 +1197,7 @@ public: moz_free(p); } - CompressedGlyph *GetCharacterGlyphs() { + virtual CompressedGlyph *GetCharacterGlyphs() MOZ_OVERRIDE { return &mCharGlyphsStorage[0]; } diff --git a/image/src/ImageFactory.cpp b/image/src/ImageFactory.cpp index 8c6af28e8a9..26fd10f3d2d 100644 --- a/image/src/ImageFactory.cpp +++ b/image/src/ImageFactory.cpp @@ -45,7 +45,8 @@ ComputeImageFlags(ImageURL* uri, const nsCString& aMimeType, bool isMultiPart) // We default to the static globals. bool isDiscardable = gfxPrefs::ImageMemDiscardable(); - bool doDecodeOnDraw = gfxPrefs::ImageMemDecodeOnDraw(); + bool doDecodeOnDraw = gfxPrefs::ImageMemDecodeOnDraw() && + gfxPrefs::AsyncPanZoomEnabled(); bool doDownscaleDuringDecode = gfxPrefs::ImageDownscaleDuringDecodeEnabled(); // We want UI to be as snappy as possible and not to flicker. Disable @@ -64,9 +65,12 @@ ComputeImageFlags(ImageURL* uri, const nsCString& aMimeType, bool isMultiPart) isDiscardable = doDecodeOnDraw = false; } - // Downscale-during-decode is only enabled for certain content types. - if (doDownscaleDuringDecode && !ShouldDownscaleDuringDecode(aMimeType)) { + // Downscale-during-decode and decode-on-draw are only enabled for certain + // content types. + if ((doDownscaleDuringDecode || doDecodeOnDraw) && + !ShouldDownscaleDuringDecode(aMimeType)) { doDownscaleDuringDecode = false; + doDecodeOnDraw = false; } // For multipart/x-mixed-replace, we basically want a direct channel to the diff --git a/image/src/RasterImage.cpp b/image/src/RasterImage.cpp index 201a4b595c2..6f65e2dc099 100644 --- a/image/src/RasterImage.cpp +++ b/image/src/RasterImage.cpp @@ -35,6 +35,7 @@ #include "mozilla/gfx/2D.h" #include "mozilla/DebugOnly.h" +#include "mozilla/Likely.h" #include "mozilla/RefPtr.h" #include "mozilla/Move.h" #include "mozilla/MemoryReporting.h" @@ -271,6 +272,7 @@ RasterImage::RasterImage(ProgressTracker* aProgressTracker, mSourceBuffer(new SourceBuffer()), mFrameCount(0), mHasSize(false), + mBlockedOnload(false), mDecodeOnDraw(false), mTransient(false), mDiscardable(false), @@ -1166,26 +1168,58 @@ RasterImage::OnImageDataComplete(nsIRequest*, nsISupports*, nsresult aStatus, DoError(); } - // Notify our listeners, which will fire this image's load event. MOZ_ASSERT(mHasSize || mError, "Need to know size before firing load event"); MOZ_ASSERT(!mHasSize || (mProgressTracker->GetProgress() & FLAG_SIZE_AVAILABLE), "Should have notified that the size is available if we have it"); + Progress loadProgress = LoadCompleteProgress(aLastPart, mError, finalStatus); + + if (mBlockedOnload) { + // For decode-on-draw images, we want to send notifications as if we've + // already finished decoding. Otherwise some observers will never even try + // to draw. + MOZ_ASSERT(mDecodeOnDraw, "Blocked onload but not decode-on-draw"); + loadProgress |= FLAG_FRAME_COMPLETE | + FLAG_DECODE_COMPLETE | + FLAG_ONLOAD_UNBLOCKED; + } + + // Notify our listeners, which will fire this image's load event. NotifyProgress(loadProgress); return finalStatus; } +void +RasterImage::BlockOnloadForDecodeOnDraw() +{ + if (mHasSourceData) { + // OnImageDataComplete got called before we got to run. No point in blocking + // onload now. + return; + } + + // Block onload. We'll unblock it in OnImageDataComplete. + mBlockedOnload = true; + NotifyProgress(FLAG_DECODE_STARTED | FLAG_ONLOAD_BLOCKED); +} + nsresult RasterImage::OnImageDataAvailable(nsIRequest*, nsISupports*, nsIInputStream* aInStr, - uint64_t, + uint64_t aOffset, uint32_t aCount) { nsresult rv; + if (MOZ_UNLIKELY(mDecodeOnDraw && aOffset == 0)) { + nsCOMPtr runnable = + NS_NewRunnableMethod(this, &RasterImage::BlockOnloadForDecodeOnDraw); + NS_DispatchToMainThread(runnable); + } + // WriteToSourceBuffer always consumes everything it gets if it doesn't run // out of memory. uint32_t bytesRead; @@ -1405,6 +1439,11 @@ RasterImage::WantDecodedFrames(const nsIntSize& aSize, uint32_t aFlags, NS_IMETHODIMP RasterImage::RequestDecode() { + // For decode-on-draw images, we only act on RequestDecodeForSize. + if (mDecodeOnDraw) { + return NS_OK; + } + return RequestDecodeForSize(mSize, DECODE_FLAGS_DEFAULT); } @@ -1417,6 +1456,11 @@ RasterImage::StartDecoding() NS_NewRunnableMethod(this, &RasterImage::StartDecoding)); } + // For decode-on-draw images, we only act on RequestDecodeForSize. + if (mDecodeOnDraw) { + return NS_OK; + } + return RequestDecodeForSize(mSize, FLAG_SYNC_DECODE); } @@ -1457,7 +1501,7 @@ bool RasterImage::IsDecoded() { // XXX(seth): We need to get rid of this; it's not reliable. - return mHasBeenDecoded || mError; + return mHasBeenDecoded || mError || (mDecodeOnDraw && mHasSourceData); } NS_IMETHODIMP diff --git a/image/src/RasterImage.h b/image/src/RasterImage.h index c139828a10e..593d0c913b0 100644 --- a/image/src/RasterImage.h +++ b/image/src/RasterImage.h @@ -242,6 +242,8 @@ public: nsresult aStatus, bool aLastPart) MOZ_OVERRIDE; + void BlockOnloadForDecodeOnDraw(); + /** * A hint of the number of bytes of source data that the image contains. If * called early on, this can help reduce copying and reallocations by @@ -387,6 +389,7 @@ private: // data // Boolean flags (clustered together to conserve space): bool mHasSize:1; // Has SetSize() been called? + bool mBlockedOnload:1; // Did send BLOCK_ONLOAD? bool mDecodeOnDraw:1; // Decoding on draw? bool mTransient:1; // Is the image short-lived? bool mDiscardable:1; // Is container discardable? diff --git a/image/src/imgRequestProxy.h b/image/src/imgRequestProxy.h index 89ef4f966d7..1c3e5c73248 100644 --- a/image/src/imgRequestProxy.h +++ b/image/src/imgRequestProxy.h @@ -145,7 +145,7 @@ protected: : mOwner(owner), mStatus(status) {} - NS_IMETHOD Run() { + NS_IMETHOD Run() MOZ_OVERRIDE { mOwner->DoCancel(mStatus); return NS_OK; } diff --git a/intl/unicharutil/util/nsUnicharUtils.h b/intl/unicharutil/util/nsUnicharUtils.h index 3f33c851da8..af4b2843c16 100644 --- a/intl/unicharutil/util/nsUnicharUtils.h +++ b/intl/unicharutil/util/nsUnicharUtils.h @@ -45,7 +45,7 @@ public: virtual int32_t operator() (const char16_t*, const char16_t*, uint32_t, - uint32_t) const; + uint32_t) const MOZ_OVERRIDE; }; class nsCaseInsensitiveUTF8StringComparator : public nsCStringComparator @@ -54,7 +54,7 @@ public: virtual int32_t operator() (const char*, const char*, uint32_t, - uint32_t) const; + uint32_t) const MOZ_OVERRIDE; }; class nsCaseInsensitiveStringArrayComparator @@ -73,7 +73,7 @@ public: virtual int operator() (const char16_t*, const char16_t*, uint32_t, - uint32_t) const; + uint32_t) const MOZ_OVERRIDE; }; inline bool diff --git a/ipc/app/moz.build b/ipc/app/moz.build index 332b54fef3a..9f699dd656a 100644 --- a/ipc/app/moz.build +++ b/ipc/app/moz.build @@ -66,6 +66,12 @@ if CONFIG['MOZ_SANDBOX'] and CONFIG['OS_TARGET'] == 'Linux': 'mozsandbox', ] + # gcc lto likes to put the top level asm in syscall.cc in a different partition + # from the function using it which breaks the build. Work around that by + # forcing there to be only one partition. + if '-flto' in CONFIG['OS_CXXFLAGS'] and not CONFIG['CLANG_CXX']: + LDFLAGS += ['--param lto-partitions=1'] + if CONFIG['_MSC_VER']: # Always enter a Windows program through wmain, whether or not we're # a console application. diff --git a/ipc/bluetooth/BluetoothDaemonConnection.cpp b/ipc/bluetooth/BluetoothDaemonConnection.cpp index 0d3ce8493a3..70ebea1fb9b 100644 --- a/ipc/bluetooth/BluetoothDaemonConnection.cpp +++ b/ipc/bluetooth/BluetoothDaemonConnection.cpp @@ -191,14 +191,22 @@ BluetoothDaemonPDUConsumer::~BluetoothDaemonPDUConsumer() // class BluetoothDaemonConnectionIO MOZ_FINAL : public UnixSocketWatcher + , public ConnectionOrientedSocketIO { public: - BluetoothDaemonConnectionIO(MessageLoop* aIOLoop, + BluetoothDaemonConnectionIO(MessageLoop* aIOLoop, int aFd, + ConnectionStatus aConnectionStatus, BluetoothDaemonConnection* aConnection, BluetoothDaemonPDUConsumer* aConsumer); SocketBase* GetSocketBase(); + // StreamSocketIOBase + // + + nsresult Accept(int aFd, + const union sockaddr_any* aAddr, socklen_t aAddrLen); + // Shutdown state // @@ -237,10 +245,11 @@ private: }; BluetoothDaemonConnectionIO::BluetoothDaemonConnectionIO( - MessageLoop* aIOLoop, + MessageLoop* aIOLoop, int aFd, + ConnectionStatus aConnectionStatus, BluetoothDaemonConnection* aConnection, BluetoothDaemonPDUConsumer* aConsumer) -: UnixSocketWatcher(aIOLoop) +: UnixSocketWatcher(aIOLoop, aFd, aConnectionStatus) , mConnection(aConnection) , mConsumer(aConsumer) , mShuttingDownOnIOThread(false) @@ -291,6 +300,30 @@ BluetoothDaemonConnectionIO::ShutdownOnIOThread() mShuttingDownOnIOThread = true; } +nsresult +BluetoothDaemonConnectionIO::Accept(int aFd, + const union sockaddr_any* aAddr, + socklen_t aAddrLen) +{ + MOZ_ASSERT(MessageLoopForIO::current() == GetIOLoop()); + MOZ_ASSERT(GetConnectionStatus() == SOCKET_IS_CONNECTING); + + // File-descriptor setup + + if (TEMP_FAILURE_RETRY(fcntl(aFd, F_SETFL, O_NONBLOCK)) < 0) { + OnError("fcntl", errno); + ScopedClose cleanupFd(aFd); + return NS_ERROR_FAILURE; + } + + SetSocket(aFd, SOCKET_IS_CONNECTED); + + // Signal success + OnConnected(); + + return NS_OK; +} + void BluetoothDaemonConnectionIO::Connect(const char* aSocketName) { @@ -519,7 +552,8 @@ BluetoothDaemonConnection::ConnectSocket(BluetoothDaemonPDUConsumer* aConsumer) SetConnectionStatus(SOCKET_CONNECTING); MessageLoop* ioLoop = XRE_GetIOMessageLoop(); - mIO = new BluetoothDaemonConnectionIO(ioLoop, this, aConsumer); + mIO = new BluetoothDaemonConnectionIO( + ioLoop, -1, UnixSocketWatcher::SOCKET_IS_CONNECTING, this, aConsumer); ioLoop->PostTask(FROM_HERE, new BluetoothDaemonConnectTask(mIO)); return NS_OK; @@ -560,5 +594,30 @@ BluetoothDaemonConnection::Send(BluetoothDaemonPDU* aPDU) return NS_OK; } +ConnectionOrientedSocketIO* +BluetoothDaemonConnection::GetIO() +{ + MOZ_ASSERT(NS_IsMainThread()); + MOZ_ASSERT(mIO); // Call |PrepareAccept| before listening for connections + + return mIO; +} + +ConnectionOrientedSocketIO* +BluetoothDaemonConnection::PrepareAccept(BluetoothDaemonPDUConsumer* aConsumer) +{ + MOZ_ASSERT(NS_IsMainThread()); + MOZ_ASSERT(!mIO); + MOZ_ASSERT(aConsumer); + + SetConnectionStatus(SOCKET_CONNECTING); + + mIO = new BluetoothDaemonConnectionIO( + XRE_GetIOMessageLoop(), -1, UnixSocketWatcher::SOCKET_IS_CONNECTING, + this, aConsumer); + + return mIO; +} + } } diff --git a/ipc/bluetooth/BluetoothDaemonConnection.h b/ipc/bluetooth/BluetoothDaemonConnection.h index bf69fcd8d90..e20af5762de 100644 --- a/ipc/bluetooth/BluetoothDaemonConnection.h +++ b/ipc/bluetooth/BluetoothDaemonConnection.h @@ -9,6 +9,7 @@ #include "mozilla/Attributes.h" #include "mozilla/FileUtils.h" +#include "mozilla/ipc/ConnectionOrientedSocket.h" #include "mozilla/ipc/SocketBase.h" #include "nsError.h" #include "nsAutoPtr.h" @@ -105,16 +106,33 @@ protected: * PDUs. PDU receiving is performed by |BluetoothDaemonPDUConsumer|. */ class BluetoothDaemonConnection : public SocketBase + , public ConnectionOrientedSocket { public: BluetoothDaemonConnection(); virtual ~BluetoothDaemonConnection(); + // SocketBase + // + nsresult ConnectSocket(BluetoothDaemonPDUConsumer* aConsumer); void CloseSocket(); nsresult Send(BluetoothDaemonPDU* aPDU); + // ConnectionOrientedSocket + // + + virtual ConnectionOrientedSocketIO* GetIO() MOZ_OVERRIDE; + +protected: + + // Prepares an instance of |BluetoothDaemonConnection| in DISCONNECTED + // state for accepting a connection. Subclasses implementing |GetIO| + // need to call this method. + ConnectionOrientedSocketIO* + PrepareAccept(BluetoothDaemonPDUConsumer* aConsumer); + private: BluetoothDaemonConnectionIO* mIO; }; diff --git a/ipc/unixsocket/ListenSocket.cpp b/ipc/unixsocket/ListenSocket.cpp index d935d2b5351..b264f075610 100644 --- a/ipc/unixsocket/ListenSocket.cpp +++ b/ipc/unixsocket/ListenSocket.cpp @@ -225,20 +225,7 @@ ListenSocketIO::OnAccepted(int aFd, RemoveWatchers(READ_WATCHER|WRITE_WATCHER); - nsRefPtr runnable; - - if (NS_SUCCEEDED(mCOSocketIO->Accept(aFd, aAddr, aAddrLen))) { - runnable = - new SocketIOEventRunnable( - this, SocketIOEventRunnable::CONNECT_SUCCESS); - return; - } else { - runnable = - new SocketIOEventRunnable( - this, SocketIOEventRunnable::CONNECT_ERROR); - } - - NS_DispatchToMainThread(runnable); + mCOSocketIO->Accept(aFd, aAddr, aAddrLen); } void @@ -262,6 +249,12 @@ ListenSocketIO::OnListening() } AddWatchers(READ_WATCHER, true); + + /* We signal a successful 'connection' to a local address for listening. */ + nsRefPtr runnable = + new SocketIOEventRunnable( + this, SocketIOEventRunnable::CONNECT_SUCCESS); + NS_DispatchToMainThread(runnable); } void diff --git a/js/src/jit/JitFrames.cpp b/js/src/jit/JitFrames.cpp index 95d44503424..4ea5edc701e 100644 --- a/js/src/jit/JitFrames.cpp +++ b/js/src/jit/JitFrames.cpp @@ -2928,21 +2928,21 @@ JitProfilingFrameIterator::operator++() JitFrameLayout *frame = framePtr(); FrameType prevType = frame->prevType(); - if (prevType == JitFrame_IonJS) { + if (prevType == JitFrame_IonJS || prevType == JitFrame_Unwound_IonJS) { returnAddressToFp_ = frame->returnAddress(); fp_ = GetPreviousRawFrame(frame); type_ = JitFrame_IonJS; return; } - if (prevType == JitFrame_BaselineJS) { + if (prevType == JitFrame_BaselineJS || prevType == JitFrame_Unwound_BaselineJS) { returnAddressToFp_ = frame->returnAddress(); fp_ = GetPreviousRawFrame(frame); type_ = JitFrame_BaselineJS; return; } - if (prevType == JitFrame_BaselineStub) { + if (prevType == JitFrame_BaselineStub || prevType == JitFrame_Unwound_BaselineStub) { BaselineStubFrameLayout *stubFrame = GetPreviousRawFrame(frame); MOZ_ASSERT(stubFrame->prevType() == JitFrame_BaselineJS); @@ -2954,7 +2954,7 @@ JitProfilingFrameIterator::operator++() return; } - if (prevType == JitFrame_Rectifier) { + if (prevType == JitFrame_Rectifier || prevType == JitFrame_Unwound_Rectifier) { RectifierFrameLayout *rectFrame = GetPreviousRawFrame(frame); FrameType rectPrevType = rectFrame->prevType(); diff --git a/js/xpconnect/idl/nsIXPCScriptable.idl b/js/xpconnect/idl/nsIXPCScriptable.idl index e3962d1222f..0117c1439e5 100644 --- a/js/xpconnect/idl/nsIXPCScriptable.idl +++ b/js/xpconnect/idl/nsIXPCScriptable.idl @@ -156,8 +156,8 @@ class NS_NO_VTABLE nsXPCClassInfo : public nsIClassInfo, public: NS_DECLARE_STATIC_IID_ACCESSOR(NS_XPCCLASSINFO_IID) - NS_IMETHOD_(MozExternalRefCountType) AddRef() = 0; - NS_IMETHOD_(MozExternalRefCountType) Release() = 0; + NS_IMETHOD_(MozExternalRefCountType) AddRef() MOZ_OVERRIDE = 0; + NS_IMETHOD_(MozExternalRefCountType) Release() MOZ_OVERRIDE = 0; virtual void PreserveWrapper(nsISupports *aNative) = 0; }; diff --git a/layout/base/nsFrameManager.cpp b/layout/base/nsFrameManager.cpp index e415153577d..ad23dc7489a 100644 --- a/layout/base/nsFrameManager.cpp +++ b/layout/base/nsFrameManager.cpp @@ -153,7 +153,7 @@ nsFrameManager::GetPlaceholderFrameFor(const nsIFrame* aFrame) { NS_PRECONDITION(aFrame, "null param unexpected"); - if (mPlaceholderMap.ops) { + if (mPlaceholderMap.IsInitialized()) { PlaceholderMapEntry *entry = static_cast (PL_DHashTableLookup(const_cast(&mPlaceholderMap), aFrame)); @@ -171,7 +171,7 @@ nsFrameManager::RegisterPlaceholderFrame(nsPlaceholderFrame* aPlaceholderFrame) NS_PRECONDITION(aPlaceholderFrame, "null param unexpected"); NS_PRECONDITION(nsGkAtoms::placeholderFrame == aPlaceholderFrame->GetType(), "unexpected frame type"); - if (!mPlaceholderMap.ops) { + if (!mPlaceholderMap.IsInitialized()) { PL_DHashTableInit(&mPlaceholderMap, &PlaceholderMapOps, sizeof(PlaceholderMapEntry)); } @@ -193,7 +193,7 @@ nsFrameManager::UnregisterPlaceholderFrame(nsPlaceholderFrame* aPlaceholderFrame NS_PRECONDITION(nsGkAtoms::placeholderFrame == aPlaceholderFrame->GetType(), "unexpected frame type"); - if (mPlaceholderMap.ops) { + if (mPlaceholderMap.IsInitialized()) { PL_DHashTableRemove(&mPlaceholderMap, aPlaceholderFrame->GetOutOfFlowFrame()); } @@ -211,10 +211,9 @@ UnregisterPlaceholders(PLDHashTable* table, PLDHashEntryHdr* hdr, void nsFrameManager::ClearPlaceholderFrameMap() { - if (mPlaceholderMap.ops) { + if (mPlaceholderMap.IsInitialized()) { PL_DHashTableEnumerate(&mPlaceholderMap, UnregisterPlaceholders, nullptr); PL_DHashTableFinish(&mPlaceholderMap); - mPlaceholderMap.ops = nullptr; } } diff --git a/layout/base/nsFrameManagerBase.h b/layout/base/nsFrameManagerBase.h index 5f69404982f..af06ca6f4d7 100644 --- a/layout/base/nsFrameManagerBase.h +++ b/layout/base/nsFrameManagerBase.h @@ -37,7 +37,6 @@ public: , mDisplayContentsMap(nullptr) , mIsDestroyingFrames(false) { - mPlaceholderMap.ops = nullptr; } bool IsDestroyingFrames() { return mIsDestroyingFrames; } diff --git a/layout/base/nsLayoutUtils.h b/layout/base/nsLayoutUtils.h index 789dba4a027..5cfac111538 100644 --- a/layout/base/nsLayoutUtils.h +++ b/layout/base/nsLayoutUtils.h @@ -1082,14 +1082,14 @@ public: RectAccumulator(); - virtual void AddRect(const nsRect& aRect); + virtual void AddRect(const nsRect& aRect) MOZ_OVERRIDE; }; struct RectListBuilder : public RectCallback { DOMRectList* mRectList; explicit RectListBuilder(DOMRectList* aList); - virtual void AddRect(const nsRect& aRect); + virtual void AddRect(const nsRect& aRect) MOZ_OVERRIDE; }; static nsIFrame* GetContainingBlockForClientRect(nsIFrame* aFrame); diff --git a/layout/forms/test/mochitest.ini b/layout/forms/test/mochitest.ini index b6457116dc5..d1ad4decbf6 100644 --- a/layout/forms/test/mochitest.ini +++ b/layout/forms/test/mochitest.ini @@ -34,7 +34,7 @@ skip-if = (toolkit == 'gonk' && debug) #debug-only failure [test_bug564115.html] skip-if = buildapp == 'mulet' || (buildapp == 'b2g' && (toolkit != 'gonk' || debug)) || toolkit == 'android' || e10s #TIMED_OUT # b2g-debug(times out on window.open and focus event) b2g-desktop(times out on window.open and focus event) [test_bug571352.html] -skip-if = buildapp == 'mulet' || buildapp == 'b2g' || toolkit == 'android' #TIMED_OUT # b2g(shift-click multi-select not working?) b2g-debug(shift-click multi-select not working?) b2g-desktop(shift-click multi-select not working?) +skip-if = (os == 'mac' && os_version == '10.10') || buildapp == 'mulet' || buildapp == 'b2g' || toolkit == 'android' #TIMED_OUT # OS X 10.10 - bug 947690, b2g(shift-click multi-select not working?) b2g-debug(shift-click multi-select not working?) b2g-desktop(shift-click multi-select not working?) [test_bug572406.html] [test_bug572649.html] skip-if = toolkit == 'android' #TIMED_OUT diff --git a/layout/generic/nsImageFrame.cpp b/layout/generic/nsImageFrame.cpp index f8d49fdadfa..8a8d224e1e3 100644 --- a/layout/generic/nsImageFrame.cpp +++ b/layout/generic/nsImageFrame.cpp @@ -1425,8 +1425,7 @@ nsDisplayImage::GetContainer(LayerManager* aManager, nsDisplayListBuilder* aBuilder) { nsRefPtr container; - nsresult rv = mImage->GetImageContainer(aManager, getter_AddRefs(container)); - NS_ENSURE_SUCCESS(rv, nullptr); + mImage->GetImageContainer(aManager, getter_AddRefs(container)); return container.forget(); } diff --git a/layout/style/nsCSSRuleProcessor.cpp b/layout/style/nsCSSRuleProcessor.cpp index 4a976ab6316..09e05d9872b 100644 --- a/layout/style/nsCSSRuleProcessor.cpp +++ b/layout/style/nsCSSRuleProcessor.cpp @@ -218,7 +218,7 @@ RuleHash_CIMatchEntry(PLDHashTable *table, const PLDHashEntryHdr *hdr, nsIAtom *match_atom = const_cast(static_cast (key)); // Use our extra |getKey| callback to avoid code duplication. - nsIAtom *entry_atom = ToLocalOps(table->ops)->getKey(table, hdr); + nsIAtom *entry_atom = ToLocalOps(table->Ops())->getKey(table, hdr); // Check for case-sensitive match first. if (match_atom == entry_atom) @@ -240,7 +240,7 @@ RuleHash_CSMatchEntry(PLDHashTable *table, const PLDHashEntryHdr *hdr, nsIAtom *match_atom = const_cast(static_cast (key)); // Use our extra |getKey| callback to avoid code duplication. - nsIAtom *entry_atom = ToLocalOps(table->ops)->getKey(table, hdr); + nsIAtom *entry_atom = ToLocalOps(table->Ops())->getKey(table, hdr); return match_atom == entry_atom; } @@ -454,8 +454,7 @@ protected: void AppendUniversalRule(const RuleSelectorPair& aRuleInfo); int32_t mRuleCount; - // The hashtables are lazily initialized; we use a null .ops to - // indicate that they need initialization. + // The hashtables are lazily initialized. PLDHashTable mIdTable; PLDHashTable mClassTable; PLDHashTable mTagTable; @@ -514,11 +513,6 @@ RuleHash::RuleHash(bool aQuirksMode) #endif { MOZ_COUNT_CTOR(RuleHash); - - mTagTable.ops = nullptr; - mIdTable.ops = nullptr; - mClassTable.ops = nullptr; - mNameSpaceTable.ops = nullptr; } RuleHash::~RuleHash() @@ -561,16 +555,16 @@ RuleHash::~RuleHash() delete [] mEnumList; } // delete arena for strings and small objects - if (mIdTable.ops) { + if (mIdTable.IsInitialized()) { PL_DHashTableFinish(&mIdTable); } - if (mClassTable.ops) { + if (mClassTable.IsInitialized()) { PL_DHashTableFinish(&mClassTable); } - if (mTagTable.ops) { + if (mTagTable.IsInitialized()) { PL_DHashTableFinish(&mTagTable); } - if (mNameSpaceTable.ops) { + if (mNameSpaceTable.IsInitialized()) { PL_DHashTableFinish(&mNameSpaceTable); } } @@ -611,7 +605,7 @@ void RuleHash::AppendRule(const RuleSelectorPair& aRuleInfo) selector = selector->mNext; } if (nullptr != selector->mIDList) { - if (!mIdTable.ops) { + if (!mIdTable.IsInitialized()) { PL_DHashTableInit(&mIdTable, mQuirksMode ? &RuleHash_IdTable_CIOps.ops : &RuleHash_IdTable_CSOps.ops, @@ -621,7 +615,7 @@ void RuleHash::AppendRule(const RuleSelectorPair& aRuleInfo) RULE_HASH_STAT_INCREMENT(mIdSelectors); } else if (nullptr != selector->mClassList) { - if (!mClassTable.ops) { + if (!mClassTable.IsInitialized()) { PL_DHashTableInit(&mClassTable, mQuirksMode ? &RuleHash_ClassTable_CIOps.ops : &RuleHash_ClassTable_CSOps.ops, @@ -632,7 +626,7 @@ void RuleHash::AppendRule(const RuleSelectorPair& aRuleInfo) } else if (selector->mLowercaseTag) { RuleValue ruleValue(aRuleInfo, mRuleCount++, mQuirksMode); - if (!mTagTable.ops) { + if (!mTagTable.IsInitialized()) { PL_DHashTableInit(&mTagTable, &RuleHash_TagTable_Ops, sizeof(RuleHashTagTableEntry)); } @@ -645,7 +639,7 @@ void RuleHash::AppendRule(const RuleSelectorPair& aRuleInfo) } } else if (kNameSpaceID_Unknown != selector->mNameSpace) { - if (!mNameSpaceTable.ops) { + if (!mNameSpaceTable.IsInitialized()) { PL_DHashTableInit(&mNameSpaceTable, &RuleHash_NameSpaceTable_Ops, sizeof(RuleHashTableEntry)); } @@ -705,7 +699,7 @@ void RuleHash::EnumerateAllRules(Element* aElement, ElementDependentRuleProcesso RULE_HASH_STAT_INCREMENT_LIST_COUNT(mUniversalRules, mElementUniversalCalls); } // universal rules within the namespace - if (kNameSpaceID_Unknown != nameSpace && mNameSpaceTable.ops) { + if (kNameSpaceID_Unknown != nameSpace && mNameSpaceTable.IsInitialized()) { RuleHashTableEntry *entry = static_cast (PL_DHashTableLookup(&mNameSpaceTable, NS_INT32_TO_PTR(nameSpace))); if (PL_DHASH_ENTRY_IS_BUSY(entry)) { @@ -713,7 +707,7 @@ void RuleHash::EnumerateAllRules(Element* aElement, ElementDependentRuleProcesso RULE_HASH_STAT_INCREMENT_LIST_COUNT(entry->mRules, mElementNameSpaceCalls); } } - if (mTagTable.ops) { + if (mTagTable.IsInitialized()) { RuleHashTableEntry *entry = static_cast (PL_DHashTableLookup(&mTagTable, tag)); if (PL_DHASH_ENTRY_IS_BUSY(entry)) { @@ -721,7 +715,7 @@ void RuleHash::EnumerateAllRules(Element* aElement, ElementDependentRuleProcesso RULE_HASH_STAT_INCREMENT_LIST_COUNT(entry->mRules, mElementTagCalls); } } - if (id && mIdTable.ops) { + if (id && mIdTable.IsInitialized()) { RuleHashTableEntry *entry = static_cast (PL_DHashTableLookup(&mIdTable, id)); if (PL_DHASH_ENTRY_IS_BUSY(entry)) { @@ -729,7 +723,7 @@ void RuleHash::EnumerateAllRules(Element* aElement, ElementDependentRuleProcesso RULE_HASH_STAT_INCREMENT_LIST_COUNT(entry->mRules, mElementIdCalls); } } - if (mClassTable.ops) { + if (mClassTable.IsInitialized()) { for (int32_t index = 0; index < classCount; ++index) { RuleHashTableEntry *entry = static_cast (PL_DHashTableLookup(&mClassTable, classList->AtomAt(index))); @@ -792,25 +786,25 @@ RuleHash::SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const { size_t n = 0; - if (mIdTable.ops) { + if (mIdTable.IsInitialized()) { n += PL_DHashTableSizeOfExcludingThis(&mIdTable, SizeOfRuleHashTableEntry, aMallocSizeOf); } - if (mClassTable.ops) { + if (mClassTable.IsInitialized()) { n += PL_DHashTableSizeOfExcludingThis(&mClassTable, SizeOfRuleHashTableEntry, aMallocSizeOf); } - if (mTagTable.ops) { + if (mTagTable.IsInitialized()) { n += PL_DHashTableSizeOfExcludingThis(&mTagTable, SizeOfRuleHashTableEntry, aMallocSizeOf); } - if (mNameSpaceTable.ops) { + if (mNameSpaceTable.IsInitialized()) { n += PL_DHashTableSizeOfExcludingThis(&mNameSpaceTable, SizeOfRuleHashTableEntry, aMallocSizeOf); @@ -3362,9 +3356,8 @@ struct CascadeEnumData { mCacheKey(aKey), mSheetType(aSheetType) { - if (!PL_DHashTableInit(&mRulesByWeight, &gRulesByWeightOps, - sizeof(RuleByWeightEntry), fallible_t(), 32)) - mRulesByWeight.ops = nullptr; + PL_DHashTableInit(&mRulesByWeight, &gRulesByWeightOps, + sizeof(RuleByWeightEntry), 32); // Initialize our arena PL_INIT_ARENA_POOL(&mArena, "CascadeEnumDataArena", @@ -3373,7 +3366,7 @@ struct CascadeEnumData { ~CascadeEnumData() { - if (mRulesByWeight.ops) + if (mRulesByWeight.IsInitialized()) PL_DHashTableFinish(&mRulesByWeight); PL_FinishArenaPool(&mArena); } @@ -3587,7 +3580,7 @@ nsCSSRuleProcessor::RefreshRuleCascade(nsPresContext* aPresContext) newCascade->mCounterStyleRules, newCascade->mCacheKey, mSheetType); - if (!data.mRulesByWeight.ops) + if (!data.mRulesByWeight.IsInitialized()) return; /* out of memory */ for (uint32_t i = 0; i < mSheets.Length(); ++i) { diff --git a/layout/style/nsHTMLStyleSheet.cpp b/layout/style/nsHTMLStyleSheet.cpp index 80a34b6cad8..47ead13ef41 100644 --- a/layout/style/nsHTMLStyleSheet.cpp +++ b/layout/style/nsHTMLStyleSheet.cpp @@ -238,16 +238,16 @@ nsHTMLStyleSheet::nsHTMLStyleSheet(nsIDocument* aDocument) , mTableTHRule(new TableTHRule()) { MOZ_ASSERT(aDocument); - mMappedAttrTable.ops = nullptr; - mLangRuleTable.ops = nullptr; } nsHTMLStyleSheet::~nsHTMLStyleSheet() { - if (mLangRuleTable.ops) + if (mLangRuleTable.IsInitialized()) { PL_DHashTableFinish(&mLangRuleTable); - if (mMappedAttrTable.ops) + } + if (mMappedAttrTable.IsInitialized()) { PL_DHashTableFinish(&mMappedAttrTable); + } } NS_IMPL_ISUPPORTS(nsHTMLStyleSheet, nsIStyleRuleProcessor) @@ -425,13 +425,11 @@ nsHTMLStyleSheet::Reset() mVisitedRule = nullptr; mActiveRule = nullptr; - if (mLangRuleTable.ops) { + if (mLangRuleTable.IsInitialized()) { PL_DHashTableFinish(&mLangRuleTable); - mLangRuleTable.ops = nullptr; } - if (mMappedAttrTable.ops) { + if (mMappedAttrTable.IsInitialized()) { PL_DHashTableFinish(&mMappedAttrTable); - mMappedAttrTable.ops = nullptr; } } @@ -481,7 +479,7 @@ nsHTMLStyleSheet::SetVisitedLinkColor(nscolor aColor) already_AddRefed nsHTMLStyleSheet::UniqueMappedAttributes(nsMappedAttributes* aMapped) { - if (!mMappedAttrTable.ops) { + if (!mMappedAttrTable.IsInitialized()) { PL_DHashTableInit(&mMappedAttrTable, &MappedAttrTable_Ops, sizeof(MappedAttrTableEntry)); } @@ -502,7 +500,7 @@ nsHTMLStyleSheet::DropMappedAttributes(nsMappedAttributes* aMapped) { NS_ENSURE_TRUE_VOID(aMapped); - NS_ASSERTION(mMappedAttrTable.ops, "table uninitialized"); + NS_ASSERTION(mMappedAttrTable.IsInitialized(), "table uninitialized"); #ifdef DEBUG uint32_t entryCount = mMappedAttrTable.EntryCount() - 1; #endif @@ -515,7 +513,7 @@ nsHTMLStyleSheet::DropMappedAttributes(nsMappedAttributes* aMapped) nsIStyleRule* nsHTMLStyleSheet::LangRuleFor(const nsString& aLanguage) { - if (!mLangRuleTable.ops) { + if (!mLangRuleTable.IsInitialized()) { PL_DHashTableInit(&mLangRuleTable, &LangRuleTable_Ops, sizeof(LangRuleTableEntry)); } @@ -545,7 +543,7 @@ nsHTMLStyleSheet::DOMSizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const { size_t n = aMallocSizeOf(this); - if (mMappedAttrTable.ops) { + if (mMappedAttrTable.IsInitialized()) { n += PL_DHashTableSizeOfExcludingThis(&mMappedAttrTable, SizeOfAttributesEntryExcludingThis, aMallocSizeOf); diff --git a/layout/tables/SpanningCellSorter.cpp b/layout/tables/SpanningCellSorter.cpp index a9f7c542b02..8a4c015cb28 100644 --- a/layout/tables/SpanningCellSorter.cpp +++ b/layout/tables/SpanningCellSorter.cpp @@ -19,14 +19,12 @@ SpanningCellSorter::SpanningCellSorter() , mSortedHashTable(nullptr) { memset(mArray, 0, sizeof(mArray)); - mHashTable.ops = nullptr; } SpanningCellSorter::~SpanningCellSorter() { - if (mHashTable.ops) { + if (mHashTable.IsInitialized()) { PL_DHashTableFinish(&mHashTable); - mHashTable.ops = nullptr; } delete [] mSortedHashTable; } @@ -72,7 +70,7 @@ SpanningCellSorter::AddCell(int32_t aColSpan, int32_t aRow, int32_t aCol) i->next = mArray[index]; mArray[index] = i; } else { - if (!mHashTable.ops) { + if (!mHashTable.IsInitialized()) { PL_DHashTableInit(&mHashTable, &HashTableOps, sizeof(HashTableEntry)); } @@ -147,7 +145,7 @@ SpanningCellSorter::GetNext(int32_t *aColSpan) /* prepare to enumerate the hash */ mState = ENUMERATING_HASH; mEnumerationIndex = 0; - if (mHashTable.ops) { + if (mHashTable.IsInitialized()) { HashTableEntry **sh = new HashTableEntry*[mHashTable.EntryCount()]; if (!sh) { @@ -162,7 +160,9 @@ SpanningCellSorter::GetNext(int32_t *aColSpan) } /* fall through */ case ENUMERATING_HASH: - if (mHashTable.ops && mEnumerationIndex < mHashTable.EntryCount()) { + if (mHashTable.IsInitialized() && + mEnumerationIndex < mHashTable.EntryCount()) + { Item *result = mSortedHashTable[mEnumerationIndex]->mItems; *aColSpan = mSortedHashTable[mEnumerationIndex]->mColSpan; NS_ASSERTION(result, "holes in hash table"); diff --git a/layout/xul/nsImageBoxFrame.cpp b/layout/xul/nsImageBoxFrame.cpp index 14db5b06edf..b8185a2a435 100644 --- a/layout/xul/nsImageBoxFrame.cpp +++ b/layout/xul/nsImageBoxFrame.cpp @@ -434,8 +434,7 @@ nsImageBoxFrame::GetContainer(LayerManager* aManager) } nsRefPtr container; - nsresult rv = imgCon->GetImageContainer(aManager, getter_AddRefs(container)); - NS_ENSURE_SUCCESS(rv, nullptr); + imgCon->GetImageContainer(aManager, getter_AddRefs(container)); return container.forget(); } diff --git a/media/libstagefright/binding/Box.cpp b/media/libstagefright/binding/Box.cpp index 886345036d2..1735fa86d22 100644 --- a/media/libstagefright/binding/Box.cpp +++ b/media/libstagefright/binding/Box.cpp @@ -48,8 +48,8 @@ Box::Box(BoxContext* aContext, uint64_t aOffset, const Box* aParent) if ((mParent && !mParent->mRange.Contains(bigLengthRange)) || !byteRange->Contains(bigLengthRange) || !mContext->mSource->CachedReadAt(aOffset, bigLength, - sizeof(bigLengthRange), &bytes) || - bytes != sizeof(bigLengthRange)) { + sizeof(bigLength), &bytes) || + bytes != sizeof(bigLength)) { return; } size = BigEndian::readUint64(bigLength); @@ -94,7 +94,7 @@ Box::Read(nsTArray* aDest) { aDest->SetLength(mRange.mEnd - mChildOffset); size_t bytes; - if (!mContext->mSource->CachedReadAt(mChildOffset, &(*aDest)[0], + if (!mContext->mSource->CachedReadAt(mChildOffset, aDest->Elements(), aDest->Length(), &bytes) || bytes != aDest->Length()) { // Byte ranges are being reported incorrectly diff --git a/media/libstagefright/binding/Index.cpp b/media/libstagefright/binding/Index.cpp index aa57957b7f0..12c79a78d18 100644 --- a/media/libstagefright/binding/Index.cpp +++ b/media/libstagefright/binding/Index.cpp @@ -186,6 +186,31 @@ void SampleIterator::Seek(Microseconds aTime) mCurrentSample = syncSample; } +Microseconds +SampleIterator::GetNextKeyframeTime() +{ + nsTArray& moofs = mIndex->mMoofParser->Moofs(); + size_t sample = mCurrentSample + 1; + size_t moof = mCurrentMoof; + while (true) { + while (true) { + if (moof == moofs.Length()) { + return -1; + } + if (sample < moofs[moof].mIndex.Length()) { + break; + } + sample = 0; + ++moof; + } + if (moofs[moof].mIndex[sample].mSync) { + return moofs[moof].mIndex[sample].mDecodeTime; + } + ++sample; + } + MOZ_ASSERT(false); // should not be reached. +} + Index::Index(const stagefright::Vector& aIndex, Stream* aSource, uint32_t aTrackId, Microseconds aTimestampOffset, Monitor* aMonitor) diff --git a/media/libstagefright/binding/MoofParser.cpp b/media/libstagefright/binding/MoofParser.cpp index 39876e9529a..e73f7bc1a8d 100644 --- a/media/libstagefright/binding/MoofParser.cpp +++ b/media/libstagefright/binding/MoofParser.cpp @@ -286,21 +286,43 @@ public: void Moof::ParseTrun(Box& aBox, Tfhd& aTfhd, Tfdt& aTfdt, Mdhd& aMdhd, Edts& aEdts) { - if (!aMdhd.mTimescale) { + if (!aTfhd.IsValid() || !aTfdt.IsValid() || + !aMdhd.IsValid() || !aEdts.IsValid()) { return; } BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); if ((flags & 0x404) == 0x404) { // Can't use these flags together reader->DiscardRemaining(); + mValid = true; return; } uint8_t version = flags >> 24; + if (!reader->CanReadType()) { + return; + } uint32_t sampleCount = reader->ReadU32(); if (sampleCount == 0) { + mValid = true; + return; + } + + size_t need = + ((flags & 1) ? sizeof(uint32_t) : 0) + + ((flags & 4) ? sizeof(uint32_t) : 0); + uint16_t flag[] = { 0x100, 0x200, 0x400, 0x800, 0 }; + for (size_t i = 0; flag[i]; i++) { + if (flags & flag[i]) { + need += sizeof(uint32_t) * sampleCount; + } + } + if (reader->Remaining() < need) { return; } @@ -354,13 +376,22 @@ Moof::ParseTrun(Box& aBox, Tfhd& aTfhd, Tfdt& aTfdt, Mdhd& aMdhd, Edts& aEdts) } mTimeRange = Interval(ctsOrder[0]->mCompositionRange.start, ctsOrder.LastElement()->mCompositionRange.end); + mValid = true; } Tkhd::Tkhd(Box& aBox) { BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); uint8_t version = flags >> 24; + size_t need = + 3*(version ? sizeof(int64_t) : sizeof(int32_t)) + 2*sizeof(int32_t); + if (reader->Remaining() < need) { + return; + } if (version == 0) { mCreationTime = reader->ReadU32(); mModificationTime = reader->ReadU32(); @@ -378,13 +409,23 @@ Tkhd::Tkhd(Box& aBox) } // More stuff that we don't care about reader->DiscardRemaining(); + mValid = true; } Mdhd::Mdhd(Box& aBox) { BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); uint8_t version = flags >> 24; + size_t need = + 3*(version ? sizeof(int64_t) : sizeof(int32_t)) + 2*sizeof(uint32_t); + if (reader->Remaining() < need) { + return; + } + if (version == 0) { mCreationTime = reader->ReadU32(); mModificationTime = reader->ReadU32(); @@ -398,17 +439,24 @@ Mdhd::Mdhd(Box& aBox) } // language and pre_defined=0 reader->ReadU32(); + if (mTimescale) { + mValid = true; + } } Trex::Trex(Box& aBox) { BoxReader reader(aBox); + if (reader->Remaining() < 6*sizeof(uint32_t)) { + return; + } mFlags = reader->ReadU32(); mTrackId = reader->ReadU32(); mDefaultSampleDescriptionIndex = reader->ReadU32(); mDefaultSampleDuration = reader->ReadU32(); mDefaultSampleSize = reader->ReadU32(); mDefaultSampleFlags = reader->ReadU32(); + mValid = true; } Tfhd::Tfhd(Box& aBox, Trex& aTrex) : Trex(aTrex) @@ -418,7 +466,20 @@ Tfhd::Tfhd(Box& aBox, Trex& aTrex) : Trex(aTrex) MOZ_ASSERT(aBox.Parent()->Parent()->IsType("moof")); BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } mFlags = reader->ReadU32(); + size_t need = sizeof(uint32_t) /* trackid */; + uint8_t flag[] = { 1, 2, 8, 0x10, 0x20, 0 }; + for (size_t i = 0; flag[i]; i++) { + if (mFlags & flag[i]) { + need += sizeof(uint32_t); + } + } + if (reader->Remaining() < need) { + return; + } mBaseDataOffset = mFlags & 1 ? reader->ReadU32() : aBox.Parent()->Parent()->Offset(); mTrackId = reader->ReadU32(); @@ -434,19 +495,28 @@ Tfhd::Tfhd(Box& aBox, Trex& aTrex) : Trex(aTrex) if (mFlags & 0x20) { mDefaultSampleFlags = reader->ReadU32(); } + mValid = true; } Tfdt::Tfdt(Box& aBox) { BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); uint8_t version = flags >> 24; + size_t need = version ? sizeof(uint64_t) : sizeof(uint32_t) ; + if (reader->Remaining() < need) { + return; + } if (version == 0) { mBaseMediaDecodeTime = reader->ReadU32(); } else if (version == 1) { mBaseMediaDecodeTime = reader->ReadU64(); } reader->DiscardRemaining(); + mValid = true; } Edts::Edts(Box& aBox) @@ -458,9 +528,16 @@ Edts::Edts(Box& aBox) } BoxReader reader(child); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); uint8_t version = flags >> 24; - + size_t need = + sizeof(uint32_t) + 2*(version ? sizeof(int64_t) : sizeof(uint32_t)); + if (reader->Remaining() < need) { + return; + } uint32_t entryCount = reader->ReadU32(); NS_ASSERTION(entryCount == 1, "Can't handle videos with multiple edits"); if (entryCount != 1) { @@ -483,9 +560,16 @@ Edts::Edts(Box& aBox) Saiz::Saiz(Box& aBox) : mAuxInfoType("sinf"), mAuxInfoTypeParameter(0) { BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); uint8_t version = flags >> 24; - + size_t need = + ((flags & 1) ? 2*sizeof(uint32_t) : 0) + sizeof(uint8_t) + sizeof(uint32_t); + if (reader->Remaining() < need) { + return; + } if (flags & 1) { mAuxInfoType = reader->ReadU32(); mAuxInfoTypeParameter = reader->ReadU32(); @@ -497,21 +581,34 @@ Saiz::Saiz(Box& aBox) : mAuxInfoType("sinf"), mAuxInfoTypeParameter(0) mSampleInfoSize.AppendElement(defaultSampleInfoSize); } } else { - reader->ReadArray(mSampleInfoSize, count); + if (!reader->ReadArray(mSampleInfoSize, count)) { + return; + } } + mValid = true; } Saio::Saio(Box& aBox) : mAuxInfoType("sinf"), mAuxInfoTypeParameter(0) { BoxReader reader(aBox); + if (!reader->CanReadType()) { + return; + } uint32_t flags = reader->ReadU32(); uint8_t version = flags >> 24; - + size_t need = ((flags & 1) ? (2*sizeof(uint32_t)) : 0) + sizeof(uint32_t); + if (reader->Remaining() < need) { + return; + } if (flags & 1) { mAuxInfoType = reader->ReadU32(); mAuxInfoTypeParameter = reader->ReadU32(); } size_t count = reader->ReadU32(); + need = (version ? sizeof(uint64_t) : sizeof(uint32_t)) * count; + if (reader->Remaining() < count) { + return; + } mOffsets.SetCapacity(count); if (version == 0) { for (size_t i = 0; i < count; i++) { @@ -522,5 +619,6 @@ Saio::Saio(Box& aBox) : mAuxInfoType("sinf"), mAuxInfoTypeParameter(0) mOffsets.AppendElement(reader->ReadU64()); } } + mValid = true; } } diff --git a/media/libstagefright/binding/include/mp4_demuxer/ByteReader.h b/media/libstagefright/binding/include/mp4_demuxer/ByteReader.h index 8f7e08c84fc..35d5e1aa454 100644 --- a/media/libstagefright/binding/include/mp4_demuxer/ByteReader.h +++ b/media/libstagefright/binding/include/mp4_demuxer/ByteReader.h @@ -36,14 +36,14 @@ public: void SetData(const nsTArray& aData) { MOZ_ASSERT(!mPtr && !mRemaining); - mPtr = &aData[0]; + mPtr = aData.Elements(); mRemaining = aData.Length(); mLength = mRemaining; } ~ByteReader() { - MOZ_ASSERT(!mRemaining); + NS_ASSERTION(!mRemaining, "Not all bytes have been processed"); } size_t Offset() diff --git a/media/libstagefright/binding/include/mp4_demuxer/Index.h b/media/libstagefright/binding/include/mp4_demuxer/Index.h index eb9ac609b1d..4ac33fe342e 100644 --- a/media/libstagefright/binding/include/mp4_demuxer/Index.h +++ b/media/libstagefright/binding/include/mp4_demuxer/Index.h @@ -22,6 +22,7 @@ public: explicit SampleIterator(Index* aIndex); MP4Sample* GetNext(); void Seek(Microseconds aTime); + Microseconds GetNextKeyframeTime(); private: Sample* Get(); diff --git a/media/libstagefright/binding/include/mp4_demuxer/MoofParser.h b/media/libstagefright/binding/include/mp4_demuxer/MoofParser.h index e76e22297c3..94bfd2d5ea2 100644 --- a/media/libstagefright/binding/include/mp4_demuxer/MoofParser.h +++ b/media/libstagefright/binding/include/mp4_demuxer/MoofParser.h @@ -16,7 +16,22 @@ class Box; class BoxContext; class Moof; -class Tkhd +class Atom +{ +public: + Atom() + : mValid(false) + { + } + virtual bool IsValid() + { + return mValid; + } +protected: + bool mValid; +}; + +class Tkhd : public Atom { public: Tkhd() @@ -34,7 +49,7 @@ public: uint64_t mDuration; }; -class Mdhd +class Mdhd : public Atom { public: Mdhd() @@ -57,7 +72,7 @@ public: uint64_t mDuration; }; -class Trex +class Trex : public Atom { public: explicit Trex(uint32_t aTrackId) @@ -83,26 +98,42 @@ public: class Tfhd : public Trex { public: - explicit Tfhd(Trex& aTrex) : Trex(aTrex), mBaseDataOffset(0) {} + explicit Tfhd(Trex& aTrex) + : Trex(aTrex) + , mBaseDataOffset(0) + { + mValid = aTrex.IsValid(); + } Tfhd(Box& aBox, Trex& aTrex); uint64_t mBaseDataOffset; }; -class Tfdt +class Tfdt : public Atom { public: - Tfdt() : mBaseMediaDecodeTime(0) {} + Tfdt() + : mBaseMediaDecodeTime(0) + { + } explicit Tfdt(Box& aBox); uint64_t mBaseMediaDecodeTime; }; -class Edts +class Edts : public Atom { public: - Edts() : mMediaStart(0) {} + Edts() + : mMediaStart(0) + { + } explicit Edts(Box& aBox); + virtual bool IsValid() + { + // edts is optional + return true; + } int64_t mMediaStart; }; @@ -116,7 +147,7 @@ struct Sample bool mSync; }; -class Saiz +class Saiz : public Atom { public: explicit Saiz(Box& aBox); @@ -126,7 +157,7 @@ public: nsTArray mSampleInfoSize; }; -class Saio +class Saio : public Atom { public: explicit Saio(Box& aBox); @@ -142,13 +173,12 @@ public: bool GetByteRanges(nsTArray* aByteRanges); private: - int64_t mMoofOffset; Saiz& mSaiz; Saio& mSaio; }; -class Moof +class Moof : public Atom { public: Moof(Box& aBox, Trex& aTrex, Mdhd& aMdhd, Edts& aEdts, Microseconds aTimestampOffset); diff --git a/media/libstagefright/binding/include/mp4_demuxer/mp4_demuxer.h b/media/libstagefright/binding/include/mp4_demuxer/mp4_demuxer.h index 7d068501653..d87d31b1d87 100644 --- a/media/libstagefright/binding/include/mp4_demuxer/mp4_demuxer.h +++ b/media/libstagefright/binding/include/mp4_demuxer/mp4_demuxer.h @@ -73,6 +73,10 @@ public: int64_t GetEvictionOffset(Microseconds aTime); + // Returns timestamp of next keyframe, or -1 if demuxer can't + // report this. + Microseconds GetNextKeyframeTime(); + private: AudioDecoderConfig mAudioConfig; VideoDecoderConfig mVideoConfig; @@ -84,6 +88,7 @@ private: nsTArray> mCachedTimeRanges; Microseconds mTimestampOffset; Monitor* mMonitor; + Microseconds mNextKeyframeTime; }; } // namespace mozilla diff --git a/media/libstagefright/binding/mp4_demuxer.cpp b/media/libstagefright/binding/mp4_demuxer.cpp index e77e01c026e..f366c863892 100644 --- a/media/libstagefright/binding/mp4_demuxer.cpp +++ b/media/libstagefright/binding/mp4_demuxer.cpp @@ -75,7 +75,8 @@ private: MP4Demuxer::MP4Demuxer(Stream* source, Microseconds aTimestampOffset, Monitor* aMonitor) : mPrivate(new StageFrightPrivate()), mSource(source), - mTimestampOffset(aTimestampOffset), mMonitor(aMonitor) + mTimestampOffset(aTimestampOffset), mMonitor(aMonitor), + mNextKeyframeTime(-1) { mPrivate->mExtractor = new MPEG4Extractor(new DataSourceAdapter(source)); } @@ -248,6 +249,9 @@ MP4Demuxer::DemuxVideoSample() sample->crypto.mode = mVideoConfig.crypto.mode; sample->crypto.key.AppendElements(mVideoConfig.crypto.key); } + if (sample->composition_timestamp >= mNextKeyframeTime) { + mNextKeyframeTime = mPrivate->mVideoIterator->GetNextKeyframeTime(); + } } return sample.forget(); } @@ -333,4 +337,14 @@ MP4Demuxer::GetEvictionOffset(Microseconds aTime) return offset == std::numeric_limits::max() ? -1 : offset; } +Microseconds +MP4Demuxer::GetNextKeyframeTime() +{ + mMonitor->AssertCurrentThreadOwns(); + if (!mPrivate->mVideoIterator) { + return -1; + } + return mNextKeyframeTime; +} + } // namespace mp4_demuxer diff --git a/memory/build/mozmemory_wrap.c b/memory/build/mozmemory_wrap.c index ad7a1d0091f..dba3ace5639 100644 --- a/memory/build/mozmemory_wrap.c +++ b/memory/build/mozmemory_wrap.c @@ -169,4 +169,10 @@ wcsdup_impl(const wchar_t *src) wcsncpy(dst, src, len + 1); return dst; } + +void * +_aligned_malloc(size_t size, size_t alignment) +{ + return memalign_impl(alignment, size); +} #endif /* XP_WIN */ diff --git a/mobile/android/app/mobile.js b/mobile/android/app/mobile.js index d17d219b789..7212cbd6ff8 100644 --- a/mobile/android/app/mobile.js +++ b/mobile/android/app/mobile.js @@ -563,7 +563,7 @@ pref("media.fragmented-mp4.android-media-codec.enabled", true); pref("media.fragmented-mp4.android-media-codec.preferred", true); // optimize images memory usage -pref("image.mem.decodeondraw", true); +pref("image.mem.decodeondraw", false); #ifdef NIGHTLY_BUILD // Shumway component (SWF player) is disabled by default. Also see bug 904346. diff --git a/modules/libpref/Preferences.cpp b/modules/libpref/Preferences.cpp index 070043b6d2f..e00c1909e91 100644 --- a/modules/libpref/Preferences.cpp +++ b/modules/libpref/Preferences.cpp @@ -235,7 +235,7 @@ Preferences::SizeOfIncludingThisAndOtherStuff(mozilla::MallocSizeOf aMallocSizeO NS_ENSURE_TRUE(InitStaticMembers(), 0); size_t n = aMallocSizeOf(sPreferences); - if (gHashTable.ops) { + if (gHashTable.IsInitialized()) { // pref keys are allocated in a private arena, which we count elsewhere. // pref stringvals are allocated out of the same private arena. n += PL_DHashTableSizeOfExcludingThis(&gHashTable, nullptr, aMallocSizeOf); @@ -955,7 +955,7 @@ Preferences::WritePrefFile(nsIFile* aFile) uint32_t writeAmount; nsresult rv; - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; // execute a "safe" save by saving through a tempfile diff --git a/modules/libpref/init/all.js b/modules/libpref/init/all.js index 08655d9898c..95cd1ae6df2 100644 --- a/modules/libpref/init/all.js +++ b/modules/libpref/init/all.js @@ -3789,7 +3789,7 @@ pref("image.mem.discardable", true); // Prevents images from automatically being decoded on load, instead allowing // them to be decoded on demand when they are drawn. -pref("image.mem.decodeondraw", true); +pref("image.mem.decodeondraw", false); // Allows image locking of decoded image data in content processes. pref("image.mem.allow_locking_in_content_processes", true); diff --git a/modules/libpref/nsPrefBranch.cpp b/modules/libpref/nsPrefBranch.cpp index d0302b961ef..5135fe46137 100644 --- a/modules/libpref/nsPrefBranch.cpp +++ b/modules/libpref/nsPrefBranch.cpp @@ -555,7 +555,7 @@ NS_IMETHODIMP nsPrefBranch::GetChildList(const char *aStartingAt, uint32_t *aCou *aChildArray = nullptr; *aCount = 0; - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; // this will contain a list of all the pref name strings diff --git a/modules/libpref/prefapi.cpp b/modules/libpref/prefapi.cpp index a4f534086eb..9978f463f6e 100644 --- a/modules/libpref/prefapi.cpp +++ b/modules/libpref/prefapi.cpp @@ -145,11 +145,10 @@ static nsresult pref_HashPref(const char *key, PrefValue value, PrefType type, u nsresult PREF_Init() { - if (!gHashTable.ops) { + if (!gHashTable.IsInitialized()) { if (!PL_DHashTableInit(&gHashTable, &pref_HashTableOps, sizeof(PrefHashEntry), fallible_t(), PREF_HASHTABLE_INITIAL_LENGTH)) { - gHashTable.ops = nullptr; return NS_ERROR_OUT_OF_MEMORY; } @@ -182,9 +181,8 @@ void PREF_Cleanup() /* Frees up all the objects except the callback list. */ void PREF_CleanupPrefs() { - if (gHashTable.ops) { + if (gHashTable.IsInitialized()) { PL_DHashTableFinish(&gHashTable); - gHashTable.ops = nullptr; PL_FinishArenaPool(&gPrefNameArena); } } @@ -466,7 +464,7 @@ pref_CompareStrings(const void *v1, const void *v2, void *unused) bool PREF_HasUserPref(const char *pref_name) { - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return false; PrefHashEntry *pref = pref_HashTableLookup(pref_name); @@ -480,7 +478,7 @@ bool PREF_HasUserPref(const char *pref_name) nsresult PREF_CopyCharPref(const char *pref_name, char ** return_buffer, bool get_default) { - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; nsresult rv = NS_ERROR_UNEXPECTED; @@ -504,7 +502,7 @@ PREF_CopyCharPref(const char *pref_name, char ** return_buffer, bool get_default nsresult PREF_GetIntPref(const char *pref_name,int32_t * return_int, bool get_default) { - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; nsresult rv = NS_ERROR_UNEXPECTED; @@ -528,7 +526,7 @@ nsresult PREF_GetIntPref(const char *pref_name,int32_t * return_int, bool get_de nsresult PREF_GetBoolPref(const char *pref_name, bool * return_value, bool get_default) { - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; nsresult rv = NS_ERROR_UNEXPECTED; @@ -579,7 +577,7 @@ PREF_DeleteBranch(const char *branch_name) int len = (int)strlen(branch_name); - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; /* The following check insures that if the branch name already has a "." @@ -602,7 +600,7 @@ PREF_DeleteBranch(const char *branch_name) nsresult PREF_ClearUserPref(const char *pref_name) { - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; PrefHashEntry* pref = pref_HashTableLookup(pref_name); @@ -648,7 +646,7 @@ PREF_ClearAllUserPrefs() MOZ_ASSERT(NS_IsMainThread()); #endif - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; PL_DHashTableEnumerate(&gHashTable, pref_ClearUserPref, nullptr); @@ -659,7 +657,7 @@ PREF_ClearAllUserPrefs() nsresult PREF_LockPref(const char *key, bool lockit) { - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_NOT_INITIALIZED; PrefHashEntry* pref = pref_HashTableLookup(key); @@ -745,7 +743,7 @@ nsresult pref_HashPref(const char *key, PrefValue value, PrefType type, uint32_t MOZ_ASSERT(NS_IsMainThread()); #endif - if (!gHashTable.ops) + if (!gHashTable.IsInitialized()) return NS_ERROR_OUT_OF_MEMORY; PrefHashEntry* pref = static_cast(PL_DHashTableAdd(&gHashTable, key)); @@ -836,7 +834,7 @@ pref_SizeOfPrivateData(MallocSizeOf aMallocSizeOf) PrefType PREF_GetPrefType(const char *pref_name) { - if (gHashTable.ops) + if (gHashTable.IsInitialized()) { PrefHashEntry* pref = pref_HashTableLookup(pref_name); if (pref) @@ -858,7 +856,7 @@ bool PREF_PrefIsLocked(const char *pref_name) { bool result = false; - if (gIsAnyPrefLocked && gHashTable.ops) { + if (gIsAnyPrefLocked && gHashTable.IsInitialized()) { PrefHashEntry* pref = pref_HashTableLookup(pref_name); if (pref && PREF_IS_LOCKED(pref)) result = true; diff --git a/mozglue/build/mozglue.def.in b/mozglue/build/mozglue.def.in index d086b9727bd..62eb3caed48 100644 --- a/mozglue/build/mozglue.def.in +++ b/mozglue/build/mozglue.def.in @@ -15,6 +15,7 @@ EXPORTS posix_memalign=posix_memalign_impl malloc_usable_size=malloc_usable_size_impl malloc_good_size=malloc_good_size_impl + _aligned_free=free_impl #else malloc=je_malloc calloc=je_calloc @@ -23,7 +24,9 @@ EXPORTS posix_memalign=je_posix_memalign malloc_usable_size=je_malloc_usable_size malloc_good_size=je_malloc_good_size + _aligned_free=je_free #endif + _aligned_malloc strndup=wrap_strndup strdup=wrap_strdup _strdup=wrap_strdup diff --git a/netwerk/base/src/nsLoadGroup.cpp b/netwerk/base/src/nsLoadGroup.cpp index 4cc74cfcc1d..6438af325ee 100644 --- a/netwerk/base/src/nsLoadGroup.cpp +++ b/netwerk/base/src/nsLoadGroup.cpp @@ -132,11 +132,6 @@ nsLoadGroup::nsLoadGroup(nsISupports* outer) #endif LOG(("LOADGROUP [%x]: Created.\n", this)); - - // Initialize the ops in the hash to null to make sure we get - // consistent errors if someone fails to call ::Init() on an - // nsLoadGroup. - mRequests.ops = nullptr; } nsLoadGroup::~nsLoadGroup() @@ -144,7 +139,7 @@ nsLoadGroup::~nsLoadGroup() DebugOnly rv = Cancel(NS_BINDING_ABORTED); NS_ASSERTION(NS_SUCCEEDED(rv), "Cancel failed"); - if (mRequests.ops) { + if (mRequests.IsInitialized()) { PL_DHashTableFinish(&mRequests); } diff --git a/netwerk/protocol/http/nsHttp.cpp b/netwerk/protocol/http/nsHttp.cpp index 5f49d8a2a5c..8cc0162cec3 100644 --- a/netwerk/protocol/http/nsHttp.cpp +++ b/netwerk/protocol/http/nsHttp.cpp @@ -96,7 +96,7 @@ static const PLDHashTableOps ops = { nsresult nsHttp::CreateAtomTable() { - MOZ_ASSERT(!sAtomTable.ops, "atom table already initialized"); + MOZ_ASSERT(!sAtomTable.IsInitialized(), "atom table already initialized"); if (!sLock) { sLock = new Mutex("nsHttp.sLock"); @@ -107,7 +107,6 @@ nsHttp::CreateAtomTable() // headers right off the bat. if (!PL_DHashTableInit(&sAtomTable, &ops, sizeof(PLDHashEntryStub), fallible_t(), NUM_HTTP_ATOMS + 10)) { - sAtomTable.ops = nullptr; return NS_ERROR_OUT_OF_MEMORY; } @@ -135,9 +134,8 @@ nsHttp::CreateAtomTable() void nsHttp::DestroyAtomTable() { - if (sAtomTable.ops) { + if (sAtomTable.IsInitialized()) { PL_DHashTableFinish(&sAtomTable); - sAtomTable.ops = nullptr; } while (sHeapAtoms) { @@ -164,7 +162,7 @@ nsHttp::ResolveAtom(const char *str) { nsHttpAtom atom = { nullptr }; - if (!str || !sAtomTable.ops) + if (!str || !sAtomTable.IsInitialized()) return atom; MutexAutoLock lock(*sLock); diff --git a/parser/htmlparser/nsHTMLEntities.cpp b/parser/htmlparser/nsHTMLEntities.cpp index 9120ca85ad2..c372b2210f9 100644 --- a/parser/htmlparser/nsHTMLEntities.cpp +++ b/parser/htmlparser/nsHTMLEntities.cpp @@ -86,14 +86,12 @@ nsHTMLEntities::AddRefTable(void) if (!PL_DHashTableInit(&gEntityToUnicode, &EntityToUnicodeOps, sizeof(EntityNodeEntry), fallible_t(), NS_HTML_ENTITY_COUNT)) { - gEntityToUnicode.ops = nullptr; return NS_ERROR_OUT_OF_MEMORY; } if (!PL_DHashTableInit(&gUnicodeToEntity, &UnicodeToEntityOps, sizeof(EntityNodeEntry), fallible_t(), NS_HTML_ENTITY_COUNT)) { PL_DHashTableFinish(&gEntityToUnicode); - gEntityToUnicode.ops = gUnicodeToEntity.ops = nullptr; return NS_ERROR_OUT_OF_MEMORY; } for (const EntityNode *node = gEntityArray, @@ -128,27 +126,25 @@ nsHTMLEntities::AddRefTable(void) } void -nsHTMLEntities::ReleaseTable(void) +nsHTMLEntities::ReleaseTable(void) { if (--gTableRefCnt != 0) return; - if (gEntityToUnicode.ops) { + if (gEntityToUnicode.IsInitialized()) { PL_DHashTableFinish(&gEntityToUnicode); - gEntityToUnicode.ops = nullptr; } - if (gUnicodeToEntity.ops) { + if (gUnicodeToEntity.IsInitialized()) { PL_DHashTableFinish(&gUnicodeToEntity); - gUnicodeToEntity.ops = nullptr; } - } -int32_t +int32_t nsHTMLEntities::EntityToUnicode(const nsCString& aEntity) { - NS_ASSERTION(gEntityToUnicode.ops, "no lookup table, needs addref"); - if (!gEntityToUnicode.ops) + NS_ASSERTION(gEntityToUnicode.IsInitialized(), + "no lookup table, needs addref"); + if (!gEntityToUnicode.IsInitialized()) return -1; //this little piece of code exists because entities may or may not have the terminating ';'. @@ -185,7 +181,8 @@ nsHTMLEntities::EntityToUnicode(const nsAString& aEntity) { const char* nsHTMLEntities::UnicodeToEntity(int32_t aUnicode) { - NS_ASSERTION(gUnicodeToEntity.ops, "no lookup table, needs addref"); + NS_ASSERTION(gUnicodeToEntity.IsInitialized(), + "no lookup table, needs addref"); EntityNodeEntry* entry = static_cast (PL_DHashTableLookup(&gUnicodeToEntity, NS_INT32_TO_PTR(aUnicode))); diff --git a/rdf/base/nsInMemoryDataSource.cpp b/rdf/base/nsInMemoryDataSource.cpp index 29033977a4c..b32766dad99 100644 --- a/rdf/base/nsInMemoryDataSource.cpp +++ b/rdf/base/nsInMemoryDataSource.cpp @@ -780,8 +780,6 @@ InMemoryDataSource::InMemoryDataSource(nsISupports* aOuter) { NS_INIT_AGGREGATED(aOuter); - mForwardArcs.ops = nullptr; - mReverseArcs.ops = nullptr; mPropagateChanges = true; MOZ_COUNT_CTOR(InMemoryDataSource); } @@ -809,7 +807,7 @@ InMemoryDataSource::~InMemoryDataSource() fprintf(stdout, "%d - RDF: InMemoryDataSource\n", gInstanceCount); #endif - if (mForwardArcs.ops) { + if (mForwardArcs.IsInitialized()) { // This'll release all of the Assertion objects that are // associated with this data source. We only need to do this // for the forward arcs, because the reverse arcs table @@ -817,7 +815,7 @@ InMemoryDataSource::~InMemoryDataSource() PL_DHashTableEnumerate(&mForwardArcs, DeleteForwardArcsEntry, nullptr); PL_DHashTableFinish(&mForwardArcs); } - if (mReverseArcs.ops) + if (mReverseArcs.IsInitialized()) PL_DHashTableFinish(&mReverseArcs); PR_LOG(gLog, PR_LOG_NOTICE, diff --git a/rdf/base/nsRDFService.cpp b/rdf/base/nsRDFService.cpp index 94539dd8d88..612f0ddd67e 100644 --- a/rdf/base/nsRDFService.cpp +++ b/rdf/base/nsRDFService.cpp @@ -723,11 +723,6 @@ RDFServiceImpl::gRDFService; RDFServiceImpl::RDFServiceImpl() : mNamedDataSources(nullptr) { - mResources.ops = nullptr; - mLiterals.ops = nullptr; - mInts.ops = nullptr; - mDates.ops = nullptr; - mBlobs.ops = nullptr; gRDFService = this; } @@ -775,15 +770,15 @@ RDFServiceImpl::~RDFServiceImpl() PL_HashTableDestroy(mNamedDataSources); mNamedDataSources = nullptr; } - if (mResources.ops) + if (mResources.IsInitialized()) PL_DHashTableFinish(&mResources); - if (mLiterals.ops) + if (mLiterals.IsInitialized()) PL_DHashTableFinish(&mLiterals); - if (mInts.ops) + if (mInts.IsInitialized()) PL_DHashTableFinish(&mInts); - if (mDates.ops) + if (mDates.IsInitialized()) PL_DHashTableFinish(&mDates); - if (mBlobs.ops) + if (mBlobs.IsInitialized()) PL_DHashTableFinish(&mBlobs); gRDFService = nullptr; } diff --git a/security/manager/boot/src/nsSecureBrowserUIImpl.cpp b/security/manager/boot/src/nsSecureBrowserUIImpl.cpp index 936d0e07a1c..6ce493962c6 100644 --- a/security/manager/boot/src/nsSecureBrowserUIImpl.cpp +++ b/security/manager/boot/src/nsSecureBrowserUIImpl.cpp @@ -123,7 +123,6 @@ nsSecureBrowserUIImpl::nsSecureBrowserUIImpl() , mOnStateLocationChangeReentranceDetection(0) #endif { - mTransferringRequests.ops = nullptr; ResetStateTracking(); #if defined(PR_LOGGING) @@ -134,9 +133,8 @@ nsSecureBrowserUIImpl::nsSecureBrowserUIImpl() nsSecureBrowserUIImpl::~nsSecureBrowserUIImpl() { - if (mTransferringRequests.ops) { + if (mTransferringRequests.IsInitialized()) { PL_DHashTableFinish(&mTransferringRequests); - mTransferringRequests.ops = nullptr; } } @@ -469,9 +467,8 @@ void nsSecureBrowserUIImpl::ResetStateTracking() ReentrantMonitorAutoEnter lock(mReentrantMonitor); mDocumentRequestsInProgress = 0; - if (mTransferringRequests.ops) { + if (mTransferringRequests.IsInitialized()) { PL_DHashTableFinish(&mTransferringRequests); - mTransferringRequests.ops = nullptr; } PL_DHashTableInit(&mTransferringRequests, &gMapOps, sizeof(RequestHashEntry)); } diff --git a/security/manager/ssl/src/nsCertTree.cpp b/security/manager/ssl/src/nsCertTree.cpp index e6ffa179919..f7d82d9876b 100644 --- a/security/manager/ssl/src/nsCertTree.cpp +++ b/security/manager/ssl/src/nsCertTree.cpp @@ -161,7 +161,6 @@ nsCertTree::nsCertTree() : mTreeArray(nullptr) { static NS_DEFINE_CID(kNSSComponentCID, NS_NSSCOMPONENT_CID); - mCompareCache.ops = nullptr; mNSSComponent = do_GetService(kNSSComponentCID); mOverrideService = do_GetService("@mozilla.org/security/certoverride;1"); // Might be a different service if someone is overriding the contract @@ -174,9 +173,8 @@ nsCertTree::nsCertTree() : mTreeArray(nullptr) void nsCertTree::ClearCompareHash() { - if (mCompareCache.ops) { + if (mCompareCache.IsInitialized()) { PL_DHashTableFinish(&mCompareCache); - mCompareCache.ops = nullptr; } } @@ -185,7 +183,6 @@ nsresult nsCertTree::InitCompareHash() ClearCompareHash(); if (!PL_DHashTableInit(&mCompareCache, &gMapOps, sizeof(CompareCacheHashEntryPtr), fallible_t(), 64)) { - mCompareCache.ops = nullptr; return NS_ERROR_OUT_OF_MEMORY; } return NS_OK; diff --git a/security/manager/ssl/src/nsNSSShutDown.cpp b/security/manager/ssl/src/nsNSSShutDown.cpp index 93e091384e8..f20490673ae 100644 --- a/security/manager/ssl/src/nsNSSShutDown.cpp +++ b/security/manager/ssl/src/nsNSSShutDown.cpp @@ -46,8 +46,6 @@ nsNSSShutDownList::nsNSSShutDownList() :mListLock("nsNSSShutDownList.mListLock") { mActiveSSLSockets = 0; - mPK11LogoutCancelObjects.ops = nullptr; - mObjects.ops = nullptr; PL_DHashTableInit(&mObjects, &gSetOps, sizeof(ObjectHashEntry)); PL_DHashTableInit(&mPK11LogoutCancelObjects, &gSetOps, sizeof(ObjectHashEntry)); @@ -55,13 +53,11 @@ nsNSSShutDownList::nsNSSShutDownList() nsNSSShutDownList::~nsNSSShutDownList() { - if (mObjects.ops) { + if (mObjects.IsInitialized()) { PL_DHashTableFinish(&mObjects); - mObjects.ops = nullptr; } - if (mPK11LogoutCancelObjects.ops) { + if (mPK11LogoutCancelObjects.IsInitialized()) { PL_DHashTableFinish(&mPK11LogoutCancelObjects); - mPK11LogoutCancelObjects.ops = nullptr; } PR_ASSERT(this == singleton); singleton = nullptr; diff --git a/toolkit/system/gnome/nsAlertsIconListener.cpp b/toolkit/system/gnome/nsAlertsIconListener.cpp index 59265311355..1957f8306d9 100644 --- a/toolkit/system/gnome/nsAlertsIconListener.cpp +++ b/toolkit/system/gnome/nsAlertsIconListener.cpp @@ -135,6 +135,16 @@ nsAlertsIconListener::OnLoadComplete(imgIRequest* aRequest) mIconRequest = nullptr; } + nsCOMPtr image; + rv = aRequest->GetImage(getter_AddRefs(image)); + MOZ_ASSERT(image); + + // Ask the image to decode at its intrinsic size. + int32_t width = 0, height = 0; + image->GetWidth(&width); + image->GetHeight(&height); + image->RequestDecodeForSize(nsIntSize(width, height), imgIContainer::FLAG_NONE); + return NS_OK; } @@ -227,8 +237,6 @@ nsAlertsIconListener::StartRequest(const nsAString & aImageUrl, bool aInPrivateB if (NS_FAILED(rv)) return rv; - mIconRequest->StartDecoding(); - return NS_OK; } diff --git a/uriloader/base/nsDocLoader.cpp b/uriloader/base/nsDocLoader.cpp index 312de92c05d..06b2b6689f3 100644 --- a/uriloader/base/nsDocLoader.cpp +++ b/uriloader/base/nsDocLoader.cpp @@ -139,7 +139,7 @@ nsDocLoader::SetDocLoaderParent(nsDocLoader *aParent) nsresult nsDocLoader::Init() { - if (!mRequestInfoHash.ops) { + if (!mRequestInfoHash.IsInitialized()) { return NS_ERROR_OUT_OF_MEMORY; } @@ -172,7 +172,7 @@ nsDocLoader::~nsDocLoader() PR_LOG(gDocLoaderLog, PR_LOG_DEBUG, ("DocLoader:%p: deleted.\n", this)); - if (mRequestInfoHash.ops) { + if (mRequestInfoHash.IsInitialized()) { PL_DHashTableFinish(&mRequestInfoHash); } } @@ -1380,7 +1380,7 @@ RemoveInfoCallback(PLDHashTable *table, PLDHashEntryHdr *hdr, uint32_t number, void nsDocLoader::ClearRequestInfoHash(void) { - if (!mRequestInfoHash.ops || !mRequestInfoHash.EntryCount()) { + if (!mRequestInfoHash.IsInitialized() || !mRequestInfoHash.EntryCount()) { // No hash, or the hash is empty, nothing to do here then... return; diff --git a/widget/GfxInfoCollector.h b/widget/GfxInfoCollector.h index 66c35fe9672..5d2034e5e28 100644 --- a/widget/GfxInfoCollector.h +++ b/widget/GfxInfoCollector.h @@ -78,7 +78,7 @@ class GfxInfoCollector : public GfxInfoCollectorBase public: GfxInfoCollector(T* aPointer, void (T::*aFunc)(InfoObject &obj)) : mPointer(aPointer), mFunc(aFunc) { } - virtual void GetInfo(InfoObject &obj) { + virtual void GetInfo(InfoObject &obj) MOZ_OVERRIDE { (mPointer->*mFunc)(obj); } diff --git a/widget/cocoa/nsMenuItemIconX.mm b/widget/cocoa/nsMenuItemIconX.mm index 4a14a9ab32c..d4ed69fe8cf 100644 --- a/widget/cocoa/nsMenuItemIconX.mm +++ b/widget/cocoa/nsMenuItemIconX.mm @@ -314,9 +314,6 @@ nsMenuItemIconX::LoadIcon(nsIURI* aIconURI) getter_AddRefs(mIconRequest)); if (NS_FAILED(rv)) return rv; - // We need to request the icon be decoded (bug 573583, bug 705516). - mIconRequest->StartDecoding(); - return NS_OK; NS_OBJC_END_TRY_ABORT_BLOCK_NSRESULT; @@ -331,6 +328,27 @@ nsMenuItemIconX::Notify(imgIRequest* aRequest, int32_t aType, const nsIntRect* aData) { + if (aType == imgINotificationObserver::LOAD_COMPLETE) { + // Make sure the image loaded successfully. + uint32_t status = imgIRequest::STATUS_ERROR; + if (NS_FAILED(aRequest->GetImageStatus(&status)) || + (status & imgIRequest::STATUS_ERROR)) { + mIconRequest->Cancel(NS_BINDING_ABORTED); + mIconRequest = nullptr; + return NS_ERROR_FAILURE; + } + + nsCOMPtr image; + aRequest->GetImage(getter_AddRefs(image)); + MOZ_ASSERT(image); + + // Ask the image to decode at its intrinsic size. + int32_t width = 0, height = 0; + image->GetWidth(&width); + image->GetHeight(&height); + image->RequestDecodeForSize(nsIntSize(width, height), imgIContainer::FLAG_NONE); + } + if (aType == imgINotificationObserver::FRAME_COMPLETE) { return OnFrameComplete(aRequest); } diff --git a/xpcom/base/CycleCollectedJSRuntime.h b/xpcom/base/CycleCollectedJSRuntime.h index c3845c2d403..c3bf60b30c4 100644 --- a/xpcom/base/CycleCollectedJSRuntime.h +++ b/xpcom/base/CycleCollectedJSRuntime.h @@ -29,27 +29,28 @@ namespace mozilla { class JSGCThingParticipant: public nsCycleCollectionParticipant { public: - NS_IMETHOD_(void) Root(void*) + NS_IMETHOD_(void) Root(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Don't call Root on GC things"); } - NS_IMETHOD_(void) Unlink(void*) + NS_IMETHOD_(void) Unlink(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Don't call Unlink on GC things, as they may be dead"); } - NS_IMETHOD_(void) Unroot(void*) + NS_IMETHOD_(void) Unroot(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Don't call Unroot on GC things, as they may be dead"); } - NS_IMETHOD_(void) DeleteCycleCollectable(void* aPtr) + NS_IMETHOD_(void) DeleteCycleCollectable(void* aPtr) MOZ_OVERRIDE { MOZ_ASSERT(false, "Can't directly delete a cycle collectable GC thing"); } - NS_IMETHOD Traverse(void* aPtr, nsCycleCollectionTraversalCallback& aCb); + NS_IMETHOD Traverse(void* aPtr, nsCycleCollectionTraversalCallback& aCb) + MOZ_OVERRIDE; }; class JSZoneParticipant : public nsCycleCollectionParticipant @@ -59,27 +60,28 @@ public: { } - NS_IMETHOD_(void) Root(void*) + NS_IMETHOD_(void) Root(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Don't call Root on GC things"); } - NS_IMETHOD_(void) Unlink(void*) + NS_IMETHOD_(void) Unlink(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Don't call Unlink on GC things, as they may be dead"); } - NS_IMETHOD_(void) Unroot(void*) + NS_IMETHOD_(void) Unroot(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Don't call Unroot on GC things, as they may be dead"); } - NS_IMETHOD_(void) DeleteCycleCollectable(void*) + NS_IMETHOD_(void) DeleteCycleCollectable(void*) MOZ_OVERRIDE { MOZ_ASSERT(false, "Can't directly delete a cycle collectable GC thing"); } - NS_IMETHOD Traverse(void* aPtr, nsCycleCollectionTraversalCallback& aCb); + NS_IMETHOD Traverse(void* aPtr, nsCycleCollectionTraversalCallback& aCb) + MOZ_OVERRIDE; }; class IncrementalFinalizeRunnable; diff --git a/xpcom/base/nsAutoPtr.h b/xpcom/base/nsAutoPtr.h index ff83f97a0f8..f56503c871b 100644 --- a/xpcom/base/nsAutoPtr.h +++ b/xpcom/base/nsAutoPtr.h @@ -771,7 +771,7 @@ public: } virtual nsresult NS_FASTCALL operator()(const nsIID& aIID, - void** aResult) const + void** aResult) const MOZ_OVERRIDE { nsresult status = mRawPtr ? mRawPtr->QueryInterface(aIID, aResult) : NS_ERROR_NULL_POINTER; diff --git a/xpcom/base/nsCycleCollector.cpp b/xpcom/base/nsCycleCollector.cpp index 425cc16af1d..d8245f955b7 100644 --- a/xpcom/base/nsCycleCollector.cpp +++ b/xpcom/base/nsCycleCollector.cpp @@ -832,14 +832,11 @@ private: PLDHashTable mPtrToNodeMap; public: - CCGraph() : mRootCount(0) - { - mPtrToNodeMap.ops = nullptr; - } + CCGraph() : mRootCount(0) {} ~CCGraph() { - if (mPtrToNodeMap.ops) { + if (mPtrToNodeMap.IsInitialized()) { PL_DHashTableFinish(&mPtrToNodeMap); } } @@ -858,7 +855,6 @@ public: mWeakMaps.Clear(); mRootCount = 0; PL_DHashTableFinish(&mPtrToNodeMap); - mPtrToNodeMap.ops = nullptr; } #ifdef DEBUG @@ -866,7 +862,7 @@ public: { return mNodes.IsEmpty() && mEdges.IsEmpty() && mWeakMaps.IsEmpty() && mRootCount == 0 && - !mPtrToNodeMap.ops; + !mPtrToNodeMap.IsInitialized(); } #endif diff --git a/xpcom/ds/nsAtomTable.cpp b/xpcom/ds/nsAtomTable.cpp index f00e89d1278..ae3bda994ad 100644 --- a/xpcom/ds/nsAtomTable.cpp +++ b/xpcom/ds/nsAtomTable.cpp @@ -40,8 +40,6 @@ using namespace mozilla; * XXX This should be manipulated in a threadsafe way or we should make * sure it's only manipulated from the main thread. Probably the latter * is better, since the former would hurt performance. - * - * If |gAtomTable.ops| is 0, then the table is uninitialized. */ static PLDHashTable gAtomTable; @@ -342,7 +340,7 @@ NS_PurgeAtomTable() { delete gStaticAtomTable; - if (gAtomTable.ops) { + if (gAtomTable.IsInitialized()) { #ifdef DEBUG const char* dumpAtomLeaks = PR_GetEnv("MOZ_DUMP_ATOM_LEAKS"); if (dumpAtomLeaks && *dumpAtomLeaks) { @@ -354,7 +352,6 @@ NS_PurgeAtomTable() } #endif PL_DHashTableFinish(&gAtomTable); - gAtomTable.ops = nullptr; } } @@ -403,14 +400,14 @@ AtomImpl::AtomImpl(nsStringBuffer* aStringBuffer, uint32_t aLength, AtomImpl::~AtomImpl() { - NS_PRECONDITION(gAtomTable.ops, "uninitialized atom hashtable"); + NS_PRECONDITION(gAtomTable.IsInitialized(), "uninitialized atom hashtable"); // Permanent atoms are removed from the hashtable at shutdown, and we // don't want to remove them twice. See comment above in // |AtomTableClearEntry|. if (!IsPermanentInDestructor()) { AtomTableKey key(mString, mLength, mHash); PL_DHashTableRemove(&gAtomTable, &key); - if (gAtomTable.ops && gAtomTable.EntryCount() == 0) { + if (gAtomTable.IsInitialized() && gAtomTable.EntryCount() == 0) { PL_DHashTableFinish(&gAtomTable); NS_ASSERTION(gAtomTable.EntryCount() == 0, "PL_DHashTableFinish changed the entry count"); @@ -529,7 +526,7 @@ void NS_SizeOfAtomTablesIncludingThis(MallocSizeOf aMallocSizeOf, size_t* aMain, size_t* aStatic) { - *aMain = gAtomTable.ops + *aMain = gAtomTable.IsInitialized() ? PL_DHashTableSizeOfExcludingThis(&gAtomTable, SizeOfAtomTableEntryExcludingThis, aMallocSizeOf) @@ -547,7 +544,7 @@ NS_SizeOfAtomTablesIncludingThis(MallocSizeOf aMallocSizeOf, static inline void EnsureTableExists() { - if (!gAtomTable.ops) { + if (!gAtomTable.IsInitialized()) { PL_DHashTableInit(&gAtomTable, &AtomTableOps, sizeof(AtomTableEntry), ATOM_HASHTABLE_INITIAL_LENGTH); } diff --git a/xpcom/ds/nsICollection.idl b/xpcom/ds/nsICollection.idl index 3e7c1f087d1..afa7ac7d2da 100644 --- a/xpcom/ds/nsICollection.idl +++ b/xpcom/ds/nsICollection.idl @@ -42,7 +42,8 @@ class MOZ_STACK_CLASS nsQueryElementAt : public nsCOMPtr_helper // nothing else to do here } - virtual nsresult NS_FASTCALL operator()( const nsIID& aIID, void** ) const; + virtual nsresult NS_FASTCALL operator()( const nsIID& aIID, void** ) + const MOZ_OVERRIDE; private: nsICollection* MOZ_NON_OWNING_REF mCollection; diff --git a/xpcom/ds/nsPersistentProperties.cpp b/xpcom/ds/nsPersistentProperties.cpp index f107562c406..7911b49ea67 100644 --- a/xpcom/ds/nsPersistentProperties.cpp +++ b/xpcom/ds/nsPersistentProperties.cpp @@ -469,7 +469,7 @@ nsPersistentProperties::nsPersistentProperties() nsPersistentProperties::~nsPersistentProperties() { PL_FinishArenaPool(&mArena); - if (mTable.ops) { + if (mTable.IsInitialized()) { PL_DHashTableFinish(&mTable); } } diff --git a/xpcom/ds/nsStaticNameTable.cpp b/xpcom/ds/nsStaticNameTable.cpp index 09663f72153..0e03406bd65 100644 --- a/xpcom/ds/nsStaticNameTable.cpp +++ b/xpcom/ds/nsStaticNameTable.cpp @@ -106,7 +106,6 @@ nsStaticCaseInsensitiveNameTable::nsStaticCaseInsensitiveNameTable() , mNullStr("") { MOZ_COUNT_CTOR(nsStaticCaseInsensitiveNameTable); - mNameTable.ops = nullptr; } nsStaticCaseInsensitiveNameTable::~nsStaticCaseInsensitiveNameTable() @@ -118,7 +117,7 @@ nsStaticCaseInsensitiveNameTable::~nsStaticCaseInsensitiveNameTable() } nsMemory::Free((void*)mNameArray); } - if (mNameTable.ops) { + if (mNameTable.IsInitialized()) { PL_DHashTableFinish(&mNameTable); } MOZ_COUNT_DTOR(nsStaticCaseInsensitiveNameTable); @@ -129,7 +128,7 @@ nsStaticCaseInsensitiveNameTable::Init(const char* const aNames[], int32_t aLength) { NS_ASSERTION(!mNameArray, "double Init"); - NS_ASSERTION(!mNameTable.ops, "double Init"); + NS_ASSERTION(!mNameTable.IsInitialized(), "double Init"); NS_ASSERTION(aNames, "null name table"); NS_ASSERTION(aLength, "0 length"); @@ -142,7 +141,6 @@ nsStaticCaseInsensitiveNameTable::Init(const char* const aNames[], if (!PL_DHashTableInit(&mNameTable, &nametable_CaseInsensitiveHashTableOps, sizeof(NameTableEntry), fallible_t(), aLength)) { - mNameTable.ops = nullptr; return false; } @@ -187,7 +185,7 @@ int32_t nsStaticCaseInsensitiveNameTable::Lookup(const nsACString& aName) { NS_ASSERTION(mNameArray, "not inited"); - NS_ASSERTION(mNameTable.ops, "not inited"); + NS_ASSERTION(mNameTable.IsInitialized(), "not inited"); const nsAFlatCString& str = PromiseFlatCString(aName); @@ -205,7 +203,7 @@ int32_t nsStaticCaseInsensitiveNameTable::Lookup(const nsAString& aName) { NS_ASSERTION(mNameArray, "not inited"); - NS_ASSERTION(mNameTable.ops, "not inited"); + NS_ASSERTION(mNameTable.IsInitialized(), "not inited"); const nsAFlatString& str = PromiseFlatString(aName); @@ -223,7 +221,7 @@ const nsAFlatCString& nsStaticCaseInsensitiveNameTable::GetStringValue(int32_t aIndex) { NS_ASSERTION(mNameArray, "not inited"); - NS_ASSERTION(mNameTable.ops, "not inited"); + NS_ASSERTION(mNameTable.IsInitialized(), "not inited"); if ((NOT_FOUND < aIndex) && ((uint32_t)aIndex < mNameTable.EntryCount())) { return mNameArray[aIndex]; diff --git a/xpcom/glue/nsArrayUtils.h b/xpcom/glue/nsArrayUtils.h index d380e9cd9bc..e216c18c269 100644 --- a/xpcom/glue/nsArrayUtils.h +++ b/xpcom/glue/nsArrayUtils.h @@ -22,7 +22,8 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID& aIID, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID& aIID, void**) const + MOZ_OVERRIDE; private: nsIArray* MOZ_NON_OWNING_REF mArray; diff --git a/xpcom/glue/nsBaseHashtable.h b/xpcom/glue/nsBaseHashtable.h index 75f63cb7d53..031048cc223 100644 --- a/xpcom/glue/nsBaseHashtable.h +++ b/xpcom/glue/nsBaseHashtable.h @@ -167,7 +167,7 @@ public: */ uint32_t EnumerateRead(EnumReadFunction aEnumFunc, void* aUserArg) const { - NS_ASSERTION(this->mTable.ops, + NS_ASSERTION(this->mTable.IsInitialized(), "nsBaseHashtable was not initialized properly."); s_EnumReadArgs enumData = { aEnumFunc, aUserArg }; @@ -199,7 +199,7 @@ public: */ uint32_t Enumerate(EnumFunction aEnumFunc, void* aUserArg) { - NS_ASSERTION(this->mTable.ops, + NS_ASSERTION(this->mTable.IsInitialized(), "nsBaseHashtable was not initialized properly."); s_EnumArgs enumData = { aEnumFunc, aUserArg }; diff --git a/xpcom/glue/nsComponentManagerUtils.h b/xpcom/glue/nsComponentManagerUtils.h index f8b4da2e952..aa40f6891c2 100644 --- a/xpcom/glue/nsComponentManagerUtils.h +++ b/xpcom/glue/nsComponentManagerUtils.h @@ -37,7 +37,8 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const + MOZ_OVERRIDE; private: const nsCID& mCID; @@ -56,7 +57,7 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const MOZ_OVERRIDE; private: const char* mContractID; @@ -75,7 +76,7 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const MOZ_OVERRIDE; private: nsIFactory* MOZ_NON_OWNING_REF mFactory; @@ -132,7 +133,7 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const MOZ_OVERRIDE; private: const nsCID& mCID; @@ -148,7 +149,7 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const MOZ_OVERRIDE; private: const char* mContractID; diff --git a/xpcom/glue/nsCycleCollectionParticipant.h b/xpcom/glue/nsCycleCollectionParticipant.h index 1fcf858f75b..03c8078e0ee 100644 --- a/xpcom/glue/nsCycleCollectionParticipant.h +++ b/xpcom/glue/nsCycleCollectionParticipant.h @@ -182,7 +182,7 @@ public: } NS_IMETHOD_(void) Trace(void* aPtr, const TraceCallbacks& aCb, - void* aClosure) = 0; + void* aClosure) MOZ_OVERRIDE = 0; static void NoteJSChild(JS::GCCellPtr aGCThing, const char* aName, void* aClosure); @@ -202,11 +202,11 @@ public: NS_DECLARE_STATIC_IID_ACCESSOR(NS_XPCOMCYCLECOLLECTIONPARTICIPANT_IID) - NS_IMETHOD_(void) Root(void* aPtr); - NS_IMETHOD_(void) Unroot(void* aPtr); + NS_IMETHOD_(void) Root(void* aPtr) MOZ_OVERRIDE; + NS_IMETHOD_(void) Unroot(void* aPtr) MOZ_OVERRIDE; NS_IMETHOD_(void) Trace(void* aPtr, const TraceCallbacks& aCb, - void* aClosure); + void* aClosure) MOZ_OVERRIDE; static bool CheckForRightISupports(nsISupports* aSupports); }; @@ -507,8 +507,9 @@ DowncastCCParticipant(void* aPtr) #define NS_DECL_CYCLE_COLLECTION_CLASS_BODY_NO_UNLINK(_class, _base) \ public: \ - NS_IMETHOD Traverse(void *p, nsCycleCollectionTraversalCallback &cb); \ - NS_IMETHOD_(void) DeleteCycleCollectable(void *p) \ + NS_IMETHOD Traverse(void *p, nsCycleCollectionTraversalCallback &cb) \ + MOZ_OVERRIDE; \ + NS_IMETHOD_(void) DeleteCycleCollectable(void *p) MOZ_OVERRIDE \ { \ DowncastCCParticipant<_class>(p)->DeleteCycleCollectable(); \ } \ @@ -526,7 +527,7 @@ public: \ #define NS_DECL_CYCLE_COLLECTION_CLASS_BODY(_class, _base) \ NS_DECL_CYCLE_COLLECTION_CLASS_BODY_NO_UNLINK(_class, _base) \ - NS_IMETHOD_(void) Unlink(void *p); + NS_IMETHOD_(void) Unlink(void *p) MOZ_OVERRIDE; #define NS_PARTICIPANT_AS(type, participant) \ const_cast(reinterpret_cast(participant)) @@ -573,9 +574,9 @@ public: : nsXPCOMCycleCollectionParticipant(true) {} \ private: \ NS_DECL_CYCLE_COLLECTION_CLASS_BODY(_class, _base) \ - NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed); \ - NS_IMETHOD_(bool) CanSkipInCCReal(void *p); \ - NS_IMETHOD_(bool) CanSkipThisReal(void *p); \ + NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipInCCReal(void *p) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipThisReal(void *p) MOZ_OVERRIDE; \ NS_IMPL_GET_XPCOM_CYCLE_COLLECTION_PARTICIPANT(_class) \ }; \ NS_CHECK_FOR_RIGHT_PARTICIPANT_IMPL(_class) \ @@ -590,7 +591,8 @@ class NS_CYCLE_COLLECTION_INNERCLASS : public nsXPCOMCycleCollectionParticipant \ { \ NS_DECL_CYCLE_COLLECTION_CLASS_BODY(_class, _base) \ - NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure); \ + NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure) \ + MOZ_OVERRIDE; \ NS_IMPL_GET_XPCOM_CYCLE_COLLECTION_PARTICIPANT(_class) \ }; \ NS_CHECK_FOR_RIGHT_PARTICIPANT_IMPL(_class) \ @@ -606,10 +608,10 @@ public: : nsXPCOMCycleCollectionParticipant(true) {} \ private: \ NS_DECL_CYCLE_COLLECTION_CLASS_BODY(_class, _base) \ - NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure); \ - NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed); \ - NS_IMETHOD_(bool) CanSkipInCCReal(void *p); \ - NS_IMETHOD_(bool) CanSkipThisReal(void *p); \ + NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipInCCReal(void *p) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipThisReal(void *p) MOZ_OVERRIDE; \ NS_IMPL_GET_XPCOM_CYCLE_COLLECTION_PARTICIPANT(_class) \ }; \ NS_CHECK_FOR_RIGHT_PARTICIPANT_IMPL(_class) \ @@ -640,7 +642,8 @@ static NS_CYCLE_COLLECTION_INNERCLASS NS_CYCLE_COLLECTION_INNERNAME; #define NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED_BODY_NO_UNLINK(_class, \ _base_class) \ public: \ - NS_IMETHOD Traverse(void *p, nsCycleCollectionTraversalCallback &cb); \ + NS_IMETHOD Traverse(void *p, nsCycleCollectionTraversalCallback &cb) \ + MOZ_OVERRIDE; \ static _class* Downcast(nsISupports* s) \ { \ return static_cast<_class*>(static_cast<_base_class*>( \ @@ -649,7 +652,7 @@ public: \ #define NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED_BODY(_class, _base_class) \ NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED_BODY_NO_UNLINK(_class, _base_class) \ - NS_IMETHOD_(void) Unlink(void *p); + NS_IMETHOD_(void) Unlink(void *p) MOZ_OVERRIDE; #define NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(_class, _base_class) \ class NS_CYCLE_COLLECTION_INNERCLASS \ @@ -680,7 +683,8 @@ class NS_CYCLE_COLLECTION_INNERCLASS : public NS_CYCLE_COLLECTION_CLASSNAME(_base_class) \ { \ NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED_BODY(_class, _base_class) \ - NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure); \ + NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure) \ + MOZ_OVERRIDE; \ NS_IMPL_GET_XPCOM_CYCLE_COLLECTION_PARTICIPANT(_class) \ }; \ NS_CHECK_FOR_RIGHT_PARTICIPANT_IMPL_INHERITED(_class) \ @@ -690,11 +694,12 @@ static NS_CYCLE_COLLECTION_INNERCLASS NS_CYCLE_COLLECTION_INNERNAME; #define NS_DECL_CYCLE_COLLECTION_NATIVE_CLASS_BODY(_class) \ public: \ - NS_IMETHOD_(void) Root(void *n); \ - NS_IMETHOD_(void) Unlink(void *n); \ - NS_IMETHOD_(void) Unroot(void *n); \ - NS_IMETHOD Traverse(void *n, nsCycleCollectionTraversalCallback &cb); \ - NS_IMETHOD_(void) DeleteCycleCollectable(void *n) \ + NS_IMETHOD_(void) Root(void *n) MOZ_OVERRIDE; \ + NS_IMETHOD_(void) Unlink(void *n) MOZ_OVERRIDE; \ + NS_IMETHOD_(void) Unroot(void *n) MOZ_OVERRIDE; \ + NS_IMETHOD Traverse(void *n, nsCycleCollectionTraversalCallback &cb) \ + MOZ_OVERRIDE; \ + NS_IMETHOD_(void) DeleteCycleCollectable(void *n) MOZ_OVERRIDE \ { \ DowncastCCParticipant<_class>(n)->DeleteCycleCollectable(); \ } \ @@ -736,9 +741,9 @@ static NS_CYCLE_COLLECTION_INNERCLASS NS_CYCLE_COLLECTION_INNERNAME; : nsCycleCollectionParticipant(true) {} \ private: \ NS_DECL_CYCLE_COLLECTION_NATIVE_CLASS_BODY(_class) \ - NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed); \ - NS_IMETHOD_(bool) CanSkipInCCReal(void *p); \ - NS_IMETHOD_(bool) CanSkipThisReal(void *p); \ + NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed) MOZ_OVERRIDE;\ + NS_IMETHOD_(bool) CanSkipInCCReal(void *p) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipThisReal(void *p) MOZ_OVERRIDE; \ static nsCycleCollectionParticipant* GetParticipant() \ { \ return &_class::NS_CYCLE_COLLECTION_INNERNAME; \ @@ -755,9 +760,9 @@ public: \ : nsCycleCollectionParticipant(true) {} \ private: \ NS_DECL_CYCLE_COLLECTION_NATIVE_CLASS_BODY(_class) \ - NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed); \ - NS_IMETHOD_(bool) CanSkipInCCReal(void *p); \ - NS_IMETHOD_(bool) CanSkipThisReal(void *p); \ + NS_IMETHOD_(bool) CanSkipReal(void *p, bool aRemovingAllowed) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipInCCReal(void *p) MOZ_OVERRIDE; \ + NS_IMETHOD_(bool) CanSkipThisReal(void *p) MOZ_OVERRIDE; \ static nsCycleCollectionParticipant* GetParticipant() \ { \ return &_class::NS_CYCLE_COLLECTION_INNERNAME; \ @@ -774,7 +779,8 @@ static NS_CYCLE_COLLECTION_INNERCLASS NS_CYCLE_COLLECTION_INNERNAME; : public nsScriptObjectTracer \ { \ NS_DECL_CYCLE_COLLECTION_NATIVE_CLASS_BODY(_class) \ - NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure); \ + NS_IMETHOD_(void) Trace(void *p, const TraceCallbacks &cb, void *closure) \ + MOZ_OVERRIDE; \ static MOZ_CONSTEXPR nsScriptObjectTracer* GetParticipant() \ { \ return &_class::NS_CYCLE_COLLECTION_INNERNAME; \ diff --git a/xpcom/glue/nsIWeakReferenceUtils.h b/xpcom/glue/nsIWeakReferenceUtils.h index 466f5dc5997..2964cb91f78 100644 --- a/xpcom/glue/nsIWeakReferenceUtils.h +++ b/xpcom/glue/nsIWeakReferenceUtils.h @@ -39,7 +39,8 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID& aIID, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID& aIID, void**) const + MOZ_OVERRIDE; private: nsIWeakReference* MOZ_NON_OWNING_REF mWeakPtr; diff --git a/xpcom/glue/nsServiceManagerUtils.h b/xpcom/glue/nsServiceManagerUtils.h index 026b0929f81..86d5e7da0aa 100644 --- a/xpcom/glue/nsServiceManagerUtils.h +++ b/xpcom/glue/nsServiceManagerUtils.h @@ -45,7 +45,8 @@ public: { } - virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const; + virtual nsresult NS_FASTCALL operator()(const nsIID&, void**) const + MOZ_OVERRIDE; protected: const char* mCategory; const char* mEntry; diff --git a/xpcom/glue/nsTHashtable.h b/xpcom/glue/nsTHashtable.h index bd3ccc1f3e8..34fb3328931 100644 --- a/xpcom/glue/nsTHashtable.h +++ b/xpcom/glue/nsTHashtable.h @@ -126,7 +126,8 @@ public: */ EntryType* GetEntry(KeyType aKey) const { - NS_ASSERTION(mTable.ops, "nsTHashtable was not initialized properly."); + NS_ASSERTION(mTable.IsInitialized(), + "nsTHashtable was not initialized properly."); EntryType* entry = reinterpret_cast( PL_DHashTableLookup(const_cast(&mTable), @@ -157,7 +158,8 @@ public: } EntryType* PutEntry(KeyType aKey, const fallible_t&) NS_WARN_UNUSED_RESULT { - NS_ASSERTION(mTable.ops, "nsTHashtable was not initialized properly."); + NS_ASSERTION(mTable.IsInitialized(), + "nsTHashtable was not initialized properly."); return static_cast(PL_DHashTableAdd( &mTable, EntryType::KeyToPointer(aKey))); @@ -169,7 +171,8 @@ public: */ void RemoveEntry(KeyType aKey) { - NS_ASSERTION(mTable.ops, "nsTHashtable was not initialized properly."); + NS_ASSERTION(mTable.IsInitialized(), + "nsTHashtable was not initialized properly."); PL_DHashTableRemove(&mTable, EntryType::KeyToPointer(aKey)); @@ -209,7 +212,8 @@ public: */ uint32_t EnumerateEntries(Enumerator aEnumFunc, void* aUserArg) { - NS_ASSERTION(mTable.ops, "nsTHashtable was not initialized properly."); + NS_ASSERTION(mTable.IsInitialized(), + "nsTHashtable was not initialized properly."); s_EnumArgs args = { aEnumFunc, aUserArg }; return PL_DHashTableEnumerate(&mTable, s_EnumStub, &args); @@ -220,7 +224,8 @@ public: */ void Clear() { - NS_ASSERTION(mTable.ops, "nsTHashtable was not initialized properly."); + NS_ASSERTION(mTable.IsInitialized(), + "nsTHashtable was not initialized properly."); PL_DHashTableEnumerate(&mTable, PL_DHashStubEnumRemove, nullptr); } @@ -295,8 +300,8 @@ public: */ void SwapElements(nsTHashtable& aOther) { - MOZ_ASSERT_IF(this->mTable.ops && aOther.mTable.ops, - this->mTable.ops == aOther.mTable.ops); + MOZ_ASSERT_IF(this->mTable.Ops() && aOther.mTable.Ops(), + this->mTable.Ops() == aOther.mTable.Ops()); mozilla::Swap(this->mTable, aOther.mTable); } @@ -309,7 +314,8 @@ public: */ void MarkImmutable() { - NS_ASSERTION(mTable.ops, "nsTHashtable was not initialized properly."); + NS_ASSERTION(mTable.IsInitialized(), + "nsTHashtable was not initialized properly."); PL_DHashMarkTableImmutable(&mTable); } @@ -402,13 +408,13 @@ nsTHashtable::nsTHashtable(nsTHashtable&& aOther) // Indicate that aOther is not initialized. This will make its destructor a // nop, which is what we want. - aOther.mTable.ops = nullptr; + aOther.mTable.SetOps(nullptr); } template nsTHashtable::~nsTHashtable() { - if (mTable.ops) { + if (mTable.IsInitialized()) { PL_DHashTableFinish(&mTable); } } diff --git a/xpcom/glue/pldhash.cpp b/xpcom/glue/pldhash.cpp index cdbca1e519c..28bed5965a1 100644 --- a/xpcom/glue/pldhash.cpp +++ b/xpcom/glue/pldhash.cpp @@ -27,7 +27,7 @@ /* * The following DEBUG-only code is used to assert that calls to one of - * table->ops or to an enumerator do not cause re-entry into a call that + * table->mOps or to an enumerator do not cause re-entry into a call that * can mutate the table. */ #ifdef DEBUG @@ -227,8 +227,6 @@ PLDHashTable::Init(const PLDHashTableOps* aOps, return false; } - ops = aOps; - // Compute the smallest capacity allowing |aLength| elements to be inserted // without rehashing. uint32_t capacity = MinCapacity(aLength); @@ -256,6 +254,9 @@ PLDHashTable::Init(const PLDHashTableOps* aOps, memset(mEntryStore, 0, nbytes); METER(memset(&mStats, 0, sizeof(mStats))); + // Set this only once we reach a point where we know we can't fail. + mOps = aOps; + #ifdef DEBUG mRecursionLevel = 0; #endif @@ -329,11 +330,13 @@ PLDHashTable::Finish() PLDHashEntryHdr* entry = (PLDHashEntryHdr*)entryAddr; if (ENTRY_IS_LIVE(entry)) { METER(mStats.mRemoveEnums++); - ops->clearEntry(this, entry); + mOps->clearEntry(this, entry); } entryAddr += mEntrySize; } + mOps = nullptr; + DECREMENT_RECURSION_LEVEL(this); MOZ_ASSERT(RECURSION_LEVEL_SAFE_TO_FINISH(this)); @@ -366,7 +369,7 @@ PLDHashTable::SearchTable(const void* aKey, PLDHashNumber aKeyHash, } /* Hit: return entry. */ - PLDHashMatchEntry matchEntry = ops->matchEntry; + PLDHashMatchEntry matchEntry = mOps->matchEntry; if (MATCH_ENTRY_KEYHASH(entry, aKeyHash) && matchEntry(this, entry, aKey)) { METER(mStats.mHits++); @@ -500,7 +503,7 @@ PLDHashTable::ChangeTable(int aDeltaLog2) char* oldEntryAddr; oldEntryAddr = oldEntryStore = mEntryStore; mEntryStore = newEntryStore; - PLDHashMoveEntry moveEntry = ops->moveEntry; + PLDHashMoveEntry moveEntry = mOps->moveEntry; #ifdef DEBUG mRecursionLevel = recursionLevelTmp; #endif @@ -532,7 +535,7 @@ PLDHashTable::Operate(const void* aKey, PLDHashOperator aOp) MOZ_ASSERT(aOp == PL_DHASH_LOOKUP || mRecursionLevel == 0); INCREMENT_RECURSION_LEVEL(this); - PLDHashNumber keyHash = ops->hashKey(this, aKey); + PLDHashNumber keyHash = mOps->hashKey(this, aKey); keyHash *= PL_DHASH_GOLDEN_RATIO; /* Avoid 0 and 1 hash codes, they indicate free and removed entries. */ @@ -589,7 +592,7 @@ PLDHashTable::Operate(const void* aKey, PLDHashOperator aOp) mRemovedCount--; keyHash |= COLLISION_FLAG; } - if (ops->initEntry && !ops->initEntry(this, entry, aKey)) { + if (mOps->initEntry && !mOps->initEntry(this, entry, aKey)) { /* We haven't claimed entry yet; fail with null return. */ memset(entry + 1, 0, mEntrySize - sizeof(*entry)); entry = nullptr; @@ -680,7 +683,7 @@ PLDHashTable::RawRemove(PLDHashEntryHdr* aEntry) /* Load keyHash first in case clearEntry() goofs it. */ PLDHashNumber keyHash = aEntry->keyHash; - ops->clearEntry(this, aEntry); + mOps->clearEntry(this, aEntry); if (keyHash & COLLISION_FLAG) { MARK_ENTRY_REMOVED(aEntry); mRemovedCount++; diff --git a/xpcom/glue/pldhash.h b/xpcom/glue/pldhash.h index 9041245b85d..511b722d114 100644 --- a/xpcom/glue/pldhash.h +++ b/xpcom/glue/pldhash.h @@ -128,7 +128,7 @@ typedef enum PLDHashOperator * * The return value, op, is treated as a set of flags. If op is PL_DHASH_NEXT, * then continue enumerating. If op contains PL_DHASH_REMOVE, then clear (via - * aTable->ops->clearEntry) and free entry. Then we check whether op contains + * aTable->mOps->clearEntry) and free entry. Then we check whether op contains * PL_DHASH_STOP; if so, stop enumerating and return the number of live entries * that were enumerated so far. Return the total number of live entries when * enumeration completes normally. @@ -176,14 +176,8 @@ typedef size_t (*PLDHashSizeOfEntryExcludingThisFun)( */ class PLDHashTable { -public: - /* - * Virtual operations; see below. This field is public because it's commonly - * zeroed to indicate that a table is no longer live. - */ - const PLDHashTableOps* ops; - private: + const PLDHashTableOps* mOps; /* Virtual operations; see below. */ int16_t mHashShift; /* multiplicative hash shift */ /* * |mRecursionLevel| is only used in debug builds, but is present in opt @@ -222,6 +216,29 @@ private: #endif public: + // The most important thing here is that we zero |mOps| because it's used to + // determine if Init() has been called. (The use of MOZ_CONSTEXPR means all + // the other members must be initialized too.) + MOZ_CONSTEXPR PLDHashTable() + : mOps(nullptr) + , mHashShift(0) + , mRecursionLevel(0) + , mEntrySize(0) + , mEntryCount(0) + , mRemovedCount(0) + , mGeneration(0) + , mEntryStore(nullptr) +#ifdef PL_DHASHMETER + , mStats() +#endif + {} + + bool IsInitialized() const { return !!mOps; } + + // These should be used rarely. + const PLDHashTableOps* const Ops() { return mOps; } + void SetOps(const PLDHashTableOps* aOps) { mOps = aOps; } + /* * Size in entries (gross, not net of free and removed sentinels) for table. * We store mHashShift rather than sizeLog2 to optimize the collision-free @@ -381,7 +398,7 @@ struct PLDHashTableOps }; /* - * Default implementations for the above ops. + * Default implementations for the above mOps. */ PLDHashNumber PL_DHashStringKey(PLDHashTable* aTable, const void* aKey); @@ -429,7 +446,7 @@ PLDHashTable* PL_NewDHashTable( /* * Free |aTable|'s entry storage and |aTable| itself (both via - * aTable->ops->freeTable). Use this function to destroy a PLDHashTable that + * aTable->mOps->freeTable). Use this function to destroy a PLDHashTable that * was allocated on the heap via PL_NewDHashTable(). */ void PL_DHashTableDestroy(PLDHashTable* aTable); @@ -456,9 +473,9 @@ MOZ_WARN_UNUSED_RESULT bool PL_DHashTableInit( uint32_t aLength = PL_DHASH_DEFAULT_INITIAL_LENGTH); /* - * Free |aTable|'s entry storage (via aTable->ops->freeTable). Use this function - * to destroy a PLDHashTable that is allocated on the stack or in static memory - * and was created via PL_DHashTableInit(). + * Free |aTable|'s entry storage (via aTable->mOps->freeTable). Use this + * function to destroy a PLDHashTable that is allocated on the stack or in + * static memory and was created via PL_DHashTableInit(). */ void PL_DHashTableFinish(PLDHashTable* aTable); @@ -480,7 +497,7 @@ PL_DHashTableLookup(PLDHashTable* aTable, const void* aKey); * * If entry is null upon return, then either the table is severely overloaded, * and memory can't be allocated for entry storage. Or if - * aTable->ops->initEntry is non-null, the aTable->ops->initEntry op may have + * aTable->mOps->initEntry is non-null, the aTable->mOps->initEntry op may have * returned false. * * Otherwise, aEntry->keyHash has been set so that PL_DHASH_ENTRY_IS_BUSY(entry) @@ -496,7 +513,7 @@ PL_DHashTableAdd(PLDHashTable* aTable, const void* aKey); * * PL_DHashTableRemove(table, key); * - * If key's entry is found, it is cleared (via table->ops->clearEntry) and + * If key's entry is found, it is cleared (via table->mOps->clearEntry) and * the entry is marked so that PL_DHASH_ENTRY_IS_FREE(entry). This operation * returns null unconditionally; you should ignore its return value. */ @@ -521,7 +538,7 @@ PL_DHashTableEnumerate(PLDHashTable* aTable, PLDHashEnumerator aEtor, /** * Measure the size of the table's entry storage, and if * |aSizeOfEntryExcludingThis| is non-nullptr, measure the size of things - * pointed to by entries. Doesn't measure |ops| because it's often shared + * pointed to by entries. Doesn't measure |mOps| because it's often shared * between tables. */ size_t PL_DHashTableSizeOfExcludingThis( diff --git a/xpcom/string/nsAString.h b/xpcom/string/nsAString.h index e15ae81aec9..5ad82735d3f 100644 --- a/xpcom/string/nsAString.h +++ b/xpcom/string/nsAString.h @@ -43,7 +43,7 @@ public: typedef char char_type; virtual int operator()(const char_type*, const char_type*, - uint32_t, uint32_t) const; + uint32_t, uint32_t) const MOZ_OVERRIDE; }; class nsCaseInsensitiveCStringArrayComparator diff --git a/xpcom/string/nsTSubstring.h b/xpcom/string/nsTSubstring.h index a7d5734c198..313bc9523ee 100644 --- a/xpcom/string/nsTSubstring.h +++ b/xpcom/string/nsTSubstring.h @@ -43,7 +43,7 @@ public: } virtual int operator()(const char_type*, const char_type*, - uint32_t, uint32_t) const; + uint32_t, uint32_t) const MOZ_OVERRIDE; }; /** diff --git a/xpcom/tests/TestPLDHash.cpp b/xpcom/tests/TestPLDHash.cpp index d465670c281..8609c3f5195 100644 --- a/xpcom/tests/TestPLDHash.cpp +++ b/xpcom/tests/TestPLDHash.cpp @@ -16,35 +16,70 @@ namespace TestPLDHash { static bool test_pldhash_Init_capacity_ok() { + PLDHashTable t; + + // Check that the constructor nulls |ops|. + if (t.IsInitialized()) { + return false; + } + // Try the largest allowed capacity. With PL_DHASH_MAX_CAPACITY==1<<26, this // will allocate 0.5GB of entry store on 32-bit platforms and 1GB on 64-bit // platforms. - PLDHashTable t; - bool ok = PL_DHashTableInit(&t, PL_DHashGetStubOps(), - sizeof(PLDHashEntryStub), - mozilla::fallible_t(), - PL_DHASH_MAX_INITIAL_LENGTH); - if (ok) - PL_DHashTableFinish(&t); + if (!PL_DHashTableInit(&t, PL_DHashGetStubOps(), sizeof(PLDHashEntryStub), + mozilla::fallible_t(), PL_DHASH_MAX_INITIAL_LENGTH)) { + return false; + } - return ok; + // Check that Init() sets |ops|. + if (!t.IsInitialized()) { + return false; + } + + // Check that Finish() nulls |ops|. + PL_DHashTableFinish(&t); + if (t.IsInitialized()) { + return false; + } + + return true; } static bool test_pldhash_Init_capacity_too_large() { - // Try the smallest too-large capacity. PLDHashTable t; - bool ok = PL_DHashTableInit(&t, PL_DHashGetStubOps(), - sizeof(PLDHashEntryStub), - mozilla::fallible_t(), - PL_DHASH_MAX_INITIAL_LENGTH + 1); - // Don't call PL_DHashTableDestroy(), it's not safe after Init failure. - return !ok; // expected to fail + // Check that the constructor nulls |ops|. + if (t.IsInitialized()) { + return false; + } + + // Try the smallest too-large capacity. + if (PL_DHashTableInit(&t, PL_DHashGetStubOps(), + sizeof(PLDHashEntryStub), + mozilla::fallible_t(), + PL_DHASH_MAX_INITIAL_LENGTH + 1)) { + return false; // it succeeded!? + } + // Don't call PL_DHashTableFinish() here; it's not safe after Init() failure. + + // Check that |ops| is still null. + if (t.IsInitialized()) { + return false; + } + + return true; } static bool test_pldhash_Init_overflow() { + PLDHashTable t; + + // Check that the constructor nulls |ops|. + if (t.IsInitialized()) { + return false; + } + // Try an acceptable capacity, but one whose byte size overflows uint32_t. // // Ideally we'd also try a large-but-ok capacity that almost but doesn't @@ -57,13 +92,18 @@ static bool test_pldhash_Init_overflow() char buf[1024 - sizeof(PLDHashEntryHdr)]; }; - // |nullptr| for |ops| is ok because it's unused due to the failure. - PLDHashTable t; - bool ok = PL_DHashTableInit(&t, /* ops = */nullptr, - sizeof(OneKBEntry), mozilla::fallible_t(), - PL_DHASH_MAX_INITIAL_LENGTH); + if (PL_DHashTableInit(&t, PL_DHashGetStubOps(), sizeof(OneKBEntry), + mozilla::fallible_t(), PL_DHASH_MAX_INITIAL_LENGTH)) { + return false; // it succeeded!? + } + // Don't call PL_DHashTableFinish() here; it's not safe after Init() failure. - return !ok; // expected to fail + // Check that |ops| is still null. + if (t.IsInitialized()) { + return false; + } + + return true; } // See bug 931062, we skip this test on Android due to OOM. @@ -87,16 +127,18 @@ static bool test_pldhash_grow_to_max_capacity() nullptr }; - PLDHashTable t; - bool ok = PL_DHashTableInit(&t, &ops, sizeof(PLDHashEntryStub), - mozilla::fallible_t(), 128); - if (!ok) + // This is infallible. + PLDHashTable* t = PL_NewDHashTable(&ops, sizeof(PLDHashEntryStub), 128); + + // Check that New() sets |t->ops|. + if (!t->IsInitialized()) { return false; + } // Keep inserting elements until failure occurs because the table is full. size_t numInserted = 0; while (true) { - if (!PL_DHashTableAdd(&t, (const void*)numInserted)) { + if (!PL_DHashTableAdd(t, (const void*)numInserted)) { break; } numInserted++; @@ -104,7 +146,13 @@ static bool test_pldhash_grow_to_max_capacity() // We stop when the element count is 96.875% of PL_DHASH_MAX_SIZE (see // MaxLoadOnGrowthFailure()). - return numInserted == PL_DHASH_MAX_CAPACITY - (PL_DHASH_MAX_CAPACITY >> 5); + if (numInserted != PL_DHASH_MAX_CAPACITY - (PL_DHASH_MAX_CAPACITY >> 5)) { + return false; + } + + PL_DHashTableDestroy(t); + + return true; } #endif