зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1385533 - Reserve space for one pointer in the mMutationObservers array on node slots; r=smaug
This helps avoid allocations for the first mutation observer (for example, Range) created by a caller.
This commit is contained in:
Родитель
3705f09fcf
Коммит
50fd0b7a62
|
@ -1097,7 +1097,7 @@ public:
|
|||
/**
|
||||
* A list of mutation observers
|
||||
*/
|
||||
nsTObserverArray<nsIMutationObserver*> mMutationObservers;
|
||||
nsAutoTObserverArray<nsIMutationObserver*, 1> mMutationObservers;
|
||||
|
||||
/**
|
||||
* An object implementing nsIDOMNodeList for this content (childNodes)
|
||||
|
@ -1954,7 +1954,7 @@ protected:
|
|||
return GetExistingSlots();
|
||||
}
|
||||
|
||||
nsTObserverArray<nsIMutationObserver*> *GetMutationObservers()
|
||||
nsAutoTObserverArray<nsIMutationObserver*, 1> *GetMutationObservers()
|
||||
{
|
||||
return HasSlots() ? &GetExistingSlots()->mMutationObservers : nullptr;
|
||||
}
|
||||
|
|
|
@ -59,8 +59,8 @@ using mozilla::AutoJSContext;
|
|||
if (slots && !slots->mMutationObservers.IsEmpty()) { \
|
||||
/* No need to explicitly notify the first observer first \
|
||||
since that'll happen anyway. */ \
|
||||
NS_OBSERVER_ARRAY_NOTIFY_OBSERVERS( \
|
||||
slots->mMutationObservers, nsIMutationObserver, \
|
||||
NS_OBSERVER_AUTO_ARRAY_NOTIFY_OBSERVERS( \
|
||||
slots->mMutationObservers, nsIMutationObserver, 1, \
|
||||
func_, params_); \
|
||||
} \
|
||||
ShadowRoot* shadow = ShadowRoot::FromNode(node); \
|
||||
|
@ -87,8 +87,8 @@ using mozilla::AutoJSContext;
|
|||
if (slots && !slots->mMutationObservers.IsEmpty()) { \
|
||||
/* No need to explicitly notify the first observer first \
|
||||
since that'll happen anyway. */ \
|
||||
NS_OBSERVER_ARRAY_NOTIFY_OBSERVERS_WITH_QI( \
|
||||
slots->mMutationObservers, nsIMutationObserver, \
|
||||
NS_OBSERVER_AUTO_ARRAY_NOTIFY_OBSERVERS_WITH_QI( \
|
||||
slots->mMutationObservers, nsIMutationObserver, 1, \
|
||||
nsIAnimationObserver, func_, params_); \
|
||||
} \
|
||||
ShadowRoot* shadow = ShadowRoot::FromNode(node); \
|
||||
|
@ -292,9 +292,9 @@ nsNodeUtils::LastRelease(nsINode* aNode)
|
|||
nsINode::nsSlots* slots = aNode->GetExistingSlots();
|
||||
if (slots) {
|
||||
if (!slots->mMutationObservers.IsEmpty()) {
|
||||
NS_OBSERVER_ARRAY_NOTIFY_OBSERVERS(slots->mMutationObservers,
|
||||
nsIMutationObserver,
|
||||
NodeWillBeDestroyed, (aNode));
|
||||
NS_OBSERVER_AUTO_ARRAY_NOTIFY_OBSERVERS(slots->mMutationObservers,
|
||||
nsIMutationObserver, 1,
|
||||
NodeWillBeDestroyed, (aNode));
|
||||
}
|
||||
|
||||
if (aNode->IsElement()) {
|
||||
|
|
|
@ -137,10 +137,10 @@ public:
|
|||
{
|
||||
nsINode::nsSlots* slots = aContent->GetExistingSlots();
|
||||
if (slots && !slots->mMutationObservers.IsEmpty()) {
|
||||
NS_OBSERVER_ARRAY_NOTIFY_OBSERVERS(slots->mMutationObservers,
|
||||
nsIMutationObserver,
|
||||
ParentChainChanged,
|
||||
(aContent));
|
||||
NS_OBSERVER_AUTO_ARRAY_NOTIFY_OBSERVERS(slots->mMutationObservers,
|
||||
nsIMutationObserver, 1,
|
||||
ParentChainChanged,
|
||||
(aContent));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -133,10 +133,10 @@ SVGFilterElement::IsAttributeMapped(const nsIAtom* name) const
|
|||
void
|
||||
SVGFilterElement::Invalidate()
|
||||
{
|
||||
nsTObserverArray<nsIMutationObserver*> *observers = GetMutationObservers();
|
||||
nsAutoTObserverArray<nsIMutationObserver*, 1> *observers = GetMutationObservers();
|
||||
|
||||
if (observers && !observers->IsEmpty()) {
|
||||
nsTObserverArray<nsIMutationObserver*>::ForwardIterator iter(*observers);
|
||||
nsAutoTObserverArray<nsIMutationObserver*, 1>::ForwardIterator iter(*observers);
|
||||
while (iter.HasMore()) {
|
||||
nsCOMPtr<nsIMutationObserver> obs(iter.GetNext());
|
||||
nsCOMPtr<nsISVGFilterReference> filter = do_QueryInterface(obs);
|
||||
|
|
|
@ -520,6 +520,17 @@ ImplCycleCollectionTraverse(nsCycleCollectionTraversalCallback& aCallback,
|
|||
} \
|
||||
} while(0)
|
||||
|
||||
// Note that this macro only works if the array holds pointers to XPCOM objects.
|
||||
#define NS_OBSERVER_AUTO_ARRAY_NOTIFY_OBSERVERS(array_, obstype_, num_, func_, params_) \
|
||||
do { \
|
||||
nsAutoTObserverArray<obstype_ *, num_>::ForwardIterator iter_(array_); \
|
||||
obstype_* obs_; \
|
||||
while (iter_.HasMore()) { \
|
||||
obs_ = iter_.GetNext(); \
|
||||
obs_ -> func_ params_ ; \
|
||||
} \
|
||||
} while(0)
|
||||
|
||||
#define NS_OBSERVER_ARRAY_NOTIFY_OBSERVERS_WITH_QI(array_, basetype_, obstype_, func_, params_) \
|
||||
do { \
|
||||
nsTObserverArray<basetype_ *>::ForwardIterator iter_(array_); \
|
||||
|
@ -532,4 +543,17 @@ ImplCycleCollectionTraverse(nsCycleCollectionTraversalCallback& aCallback,
|
|||
} \
|
||||
} \
|
||||
} while(0)
|
||||
|
||||
#define NS_OBSERVER_AUTO_ARRAY_NOTIFY_OBSERVERS_WITH_QI(array_, basetype_, num_, obstype_, func_, params_) \
|
||||
do { \
|
||||
nsAutoTObserverArray<basetype_ *, num_>::ForwardIterator iter_(array_); \
|
||||
basetype_* obsbase_; \
|
||||
while (iter_.HasMore()) { \
|
||||
obsbase_ = iter_.GetNext(); \
|
||||
nsCOMPtr<obstype_> obs_ = do_QueryInterface(obsbase_); \
|
||||
if (obs_) { \
|
||||
obs_ -> func_ params_ ; \
|
||||
} \
|
||||
} \
|
||||
} while(0)
|
||||
#endif // nsTObserverArray_h___
|
||||
|
|
Загрузка…
Ссылка в новой задаче