2015-05-03 22:32:37 +03:00
|
|
|
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
|
|
|
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
2012-05-21 15:12:37 +04:00
|
|
|
/* This Source Code Form is subject to the terms of the Mozilla Public
|
|
|
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
|
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
2000-05-08 18:29:44 +04:00
|
|
|
|
2006-03-31 12:00:42 +04:00
|
|
|
/*
|
|
|
|
* A class for handing out nodeinfos and ensuring sharing of them as needed.
|
|
|
|
*/
|
|
|
|
|
2000-05-08 18:29:44 +04:00
|
|
|
#ifndef nsNodeInfoManager_h___
|
|
|
|
#define nsNodeInfoManager_h___
|
|
|
|
|
2015-03-21 19:28:04 +03:00
|
|
|
#include "mozilla/Attributes.h" // for final
|
2018-03-02 02:33:52 +03:00
|
|
|
#include "mozilla/dom/NodeInfo.h"
|
2020-03-17 17:52:37 +03:00
|
|
|
#include "mozilla/dom/DOMArena.h"
|
2018-09-13 02:39:43 +03:00
|
|
|
#include "mozilla/MruCache.h"
|
2012-08-06 16:02:08 +04:00
|
|
|
#include "nsCOMPtr.h" // for member
|
|
|
|
#include "nsCycleCollectionParticipant.h" // for NS_DECL_CYCLE_*
|
2018-03-02 02:33:52 +03:00
|
|
|
#include "nsDataHashtable.h"
|
2017-08-17 02:48:52 +03:00
|
|
|
#include "nsStringFwd.h"
|
2000-05-08 18:29:44 +04:00
|
|
|
|
2017-10-03 01:05:19 +03:00
|
|
|
class nsAtom;
|
2003-10-22 02:11:49 +04:00
|
|
|
class nsIPrincipal;
|
2018-02-16 15:02:28 +03:00
|
|
|
class nsWindowSizes;
|
2012-08-06 16:02:08 +04:00
|
|
|
template <class T>
|
|
|
|
struct already_AddRefed;
|
2000-05-08 18:29:44 +04:00
|
|
|
|
2019-01-02 16:05:23 +03:00
|
|
|
namespace mozilla {
|
|
|
|
namespace dom {
|
|
|
|
class Document;
|
2020-03-17 17:52:37 +03:00
|
|
|
} // namespace dom
|
2019-01-02 16:05:23 +03:00
|
|
|
} // namespace mozilla
|
|
|
|
|
2015-03-21 19:28:04 +03:00
|
|
|
class nsNodeInfoManager final {
|
2014-06-25 06:09:15 +04:00
|
|
|
private:
|
|
|
|
~nsNodeInfoManager();
|
|
|
|
|
2000-05-08 18:29:44 +04:00
|
|
|
public:
|
|
|
|
nsNodeInfoManager();
|
2004-06-25 16:26:02 +04:00
|
|
|
|
2014-11-17 15:04:00 +03:00
|
|
|
NS_DECL_CYCLE_COLLECTION_SKIPPABLE_NATIVE_CLASS(nsNodeInfoManager)
|
2012-08-24 20:50:06 +04:00
|
|
|
|
|
|
|
NS_INLINE_DECL_CYCLE_COLLECTING_NATIVE_REFCOUNTING(nsNodeInfoManager)
|
2004-06-25 16:26:02 +04:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Initialize the nodeinfo manager with a document.
|
|
|
|
*/
|
2019-01-02 16:05:23 +03:00
|
|
|
nsresult Init(mozilla::dom::Document*);
|
2004-06-25 16:26:02 +04:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Release the reference to the document, this will be called when
|
|
|
|
* the document is going away.
|
|
|
|
*/
|
|
|
|
void DropDocumentReference();
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Methods for creating nodeinfo's from atoms and/or strings.
|
|
|
|
*/
|
2014-06-20 06:01:40 +04:00
|
|
|
already_AddRefed<mozilla::dom::NodeInfo> GetNodeInfo(
|
2017-10-03 01:05:19 +03:00
|
|
|
nsAtom* aName, nsAtom* aPrefix, int32_t aNamespaceID, uint16_t aNodeType,
|
|
|
|
nsAtom* aExtraName = nullptr);
|
|
|
|
nsresult GetNodeInfo(const nsAString& aName, nsAtom* aPrefix,
|
2012-08-22 19:56:38 +04:00
|
|
|
int32_t aNamespaceID, uint16_t aNodeType,
|
2014-06-20 06:01:40 +04:00
|
|
|
mozilla::dom::NodeInfo** aNodeInfo);
|
2017-10-03 01:05:19 +03:00
|
|
|
nsresult GetNodeInfo(const nsAString& aName, nsAtom* aPrefix,
|
2012-08-22 19:56:38 +04:00
|
|
|
const nsAString& aNamespaceURI, uint16_t aNodeType,
|
2014-06-20 06:01:40 +04:00
|
|
|
mozilla::dom::NodeInfo** aNodeInfo);
|
2004-06-25 16:26:02 +04:00
|
|
|
|
2005-09-24 22:43:15 +04:00
|
|
|
/**
|
|
|
|
* Returns the nodeinfo for text nodes. Can return null if OOM.
|
|
|
|
*/
|
2014-06-20 06:01:40 +04:00
|
|
|
already_AddRefed<mozilla::dom::NodeInfo> GetTextNodeInfo();
|
2006-01-19 06:34:18 +03:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Returns the nodeinfo for comment nodes. Can return null if OOM.
|
|
|
|
*/
|
2014-06-20 06:01:40 +04:00
|
|
|
already_AddRefed<mozilla::dom::NodeInfo> GetCommentNodeInfo();
|
2005-09-24 22:43:15 +04:00
|
|
|
|
2006-01-19 06:34:18 +03:00
|
|
|
/**
|
|
|
|
* Returns the nodeinfo for the document node. Can return null if OOM.
|
|
|
|
*/
|
2014-06-20 06:01:40 +04:00
|
|
|
already_AddRefed<mozilla::dom::NodeInfo> GetDocumentNodeInfo();
|
2006-01-19 06:34:18 +03:00
|
|
|
|
2004-06-25 16:26:02 +04:00
|
|
|
/**
|
|
|
|
* Retrieve a pointer to the document that owns this node info
|
|
|
|
* manager.
|
|
|
|
*/
|
2019-01-02 16:05:23 +03:00
|
|
|
mozilla::dom::Document* GetDocument() const { return mDocument; }
|
2004-06-25 16:26:02 +04:00
|
|
|
|
|
|
|
/**
|
2006-02-02 23:02:34 +03:00
|
|
|
* Gets the principal of the document this nodeinfo manager belongs to.
|
2004-06-25 16:26:02 +04:00
|
|
|
*/
|
2006-04-27 22:21:11 +04:00
|
|
|
nsIPrincipal* DocumentPrincipal() const {
|
|
|
|
NS_ASSERTION(mPrincipal, "How'd that happen?");
|
2006-02-02 23:02:34 +03:00
|
|
|
return mPrincipal;
|
|
|
|
}
|
|
|
|
|
2014-06-20 06:01:40 +04:00
|
|
|
void RemoveNodeInfo(mozilla::dom::NodeInfo* aNodeInfo);
|
2006-02-02 23:02:34 +03:00
|
|
|
|
2017-07-04 11:00:03 +03:00
|
|
|
/**
|
|
|
|
* Returns true if SVG nodes in this document have real SVG semantics.
|
|
|
|
*/
|
2019-07-10 00:19:41 +03:00
|
|
|
bool SVGEnabled() { return mSVGEnabled.valueOr(InternalSVGEnabled()); }
|
2017-07-04 11:00:03 +03:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Returns true if MathML nodes in this document have real MathML semantics.
|
|
|
|
*/
|
|
|
|
bool MathMLEnabled() {
|
2019-07-10 00:19:41 +03:00
|
|
|
return mMathMLEnabled.valueOr(InternalMathMLEnabled());
|
2017-07-04 11:00:03 +03:00
|
|
|
}
|
|
|
|
|
2020-03-17 17:52:37 +03:00
|
|
|
mozilla::dom::DOMArena* GetArenaAllocator() { return mArena; }
|
|
|
|
void SetArenaAllocator(mozilla::dom::DOMArena* aArena);
|
|
|
|
|
|
|
|
void* Allocate(size_t aSize);
|
|
|
|
|
|
|
|
void Free(void* aPtr) { free(aPtr); }
|
|
|
|
|
|
|
|
bool HasAllocated() { return mHasAllocated; }
|
|
|
|
|
2018-02-16 15:02:28 +03:00
|
|
|
void AddSizeOfIncludingThis(nsWindowSizes& aSizes) const;
|
|
|
|
|
2006-02-02 23:02:34 +03:00
|
|
|
protected:
|
2019-01-02 16:05:23 +03:00
|
|
|
friend class mozilla::dom::Document;
|
2006-02-02 23:02:34 +03:00
|
|
|
friend class nsXULPrototypeDocument;
|
2004-06-25 16:26:02 +04:00
|
|
|
|
|
|
|
/**
|
2006-02-02 23:02:34 +03:00
|
|
|
* Sets the principal of the document this nodeinfo manager belongs to.
|
2004-06-25 16:26:02 +04:00
|
|
|
*/
|
|
|
|
void SetDocumentPrincipal(nsIPrincipal* aPrincipal);
|
|
|
|
|
2000-05-08 18:29:44 +04:00
|
|
|
private:
|
2017-07-04 11:00:03 +03:00
|
|
|
bool InternalSVGEnabled();
|
|
|
|
bool InternalMathMLEnabled();
|
|
|
|
|
2018-03-02 02:33:52 +03:00
|
|
|
class NodeInfoInnerKey
|
|
|
|
: public nsPtrHashKey<mozilla::dom::NodeInfo::NodeInfoInner> {
|
|
|
|
public:
|
|
|
|
explicit NodeInfoInnerKey(KeyTypePointer aKey) : nsPtrHashKey(aKey) {}
|
Bug 1415980 - make hash keys movable and not copyable; r=erahm
Everything that goes in a PLDHashtable (and its derivatives, like
nsTHashtable) needs to inherit from PLDHashEntryHdr. But through a lack
of enforcement, copy constructors for these derived classes didn't
explicitly invoke the copy constructor for PLDHashEntryHdr (and the
compiler didn't invoke the copy constructor for us). Instead,
PLDHashTable explicitly copied around the bits that the copy constructor
would have.
The current setup has two problems:
1) Derived classes should be using move construction, not copy
construction, since anything that's shuffling hash table keys/entries
around will be using move construction.
2) Derived classes should take responsibility for transferring bits of
superclass state around, and not rely on something else to handle that.
The second point is not a huge problem for PLDHashTable (PLDHashTable
only has to copy PLDHashEntryHdr's bits in a single place), but future
hash table implementations that might move entries around more
aggressively would have to insert compensation code all over the
place. Additionally, if moving entries is implemented via memcpy (which
is quite common), PLDHashTable copying around bits *again* is
inefficient.
Let's fix all these problems in one go, by:
1) Explicitly declaring the set of constructors that PLDHashEntryHdr
implements (and does not implement). In particular, the copy
constructor is deleted, so any derived classes that attempt to make
themselves copyable will be detected at compile time: the compiler
will complain that the superclass type is not copyable.
This change on its own will result in many compiler errors, so...
2) Change any derived classes to implement move constructors instead of
copy constructors. Note that some of these move constructors are,
strictly speaking, unnecessary, since the relevant classes are moved
via memcpy in nsTHashtable and its derivatives.
2018-09-20 18:20:36 +03:00
|
|
|
NodeInfoInnerKey(NodeInfoInnerKey&&) = default;
|
2018-03-02 02:33:52 +03:00
|
|
|
~NodeInfoInnerKey() = default;
|
|
|
|
bool KeyEquals(KeyTypePointer aKey) const { return *mKey == *aKey; }
|
|
|
|
static PLDHashNumber HashKey(KeyTypePointer aKey) { return aKey->Hash(); }
|
|
|
|
};
|
|
|
|
|
2018-09-13 02:39:43 +03:00
|
|
|
struct NodeInfoCache
|
|
|
|
: public mozilla::MruCache<mozilla::dom::NodeInfo::NodeInfoInner,
|
|
|
|
mozilla::dom::NodeInfo*, NodeInfoCache> {
|
|
|
|
static mozilla::HashNumber Hash(
|
|
|
|
const mozilla::dom::NodeInfo::NodeInfoInner& aKey) {
|
|
|
|
return aKey.Hash();
|
|
|
|
}
|
|
|
|
static bool Match(const mozilla::dom::NodeInfo::NodeInfoInner& aKey,
|
|
|
|
const mozilla::dom::NodeInfo* aVal) {
|
|
|
|
return aKey == aVal->mInner;
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2018-03-02 02:33:52 +03:00
|
|
|
nsDataHashtable<NodeInfoInnerKey, mozilla::dom::NodeInfo*> mNodeInfoHash;
|
2019-01-02 16:05:23 +03:00
|
|
|
mozilla::dom::Document* MOZ_NON_OWNING_REF mDocument; // WEAK
|
2012-08-22 19:56:38 +04:00
|
|
|
uint32_t mNonDocumentNodeInfos;
|
2014-04-10 18:05:20 +04:00
|
|
|
nsCOMPtr<nsIPrincipal> mPrincipal; // Never null after Init() succeeds.
|
2006-04-04 01:20:02 +04:00
|
|
|
nsCOMPtr<nsIPrincipal> mDefaultPrincipal; // Never null after Init() succeeds
|
2015-04-17 04:18:25 +03:00
|
|
|
mozilla::dom::NodeInfo* MOZ_NON_OWNING_REF
|
|
|
|
mTextNodeInfo; // WEAK to avoid circular ownership
|
|
|
|
mozilla::dom::NodeInfo* MOZ_NON_OWNING_REF
|
|
|
|
mCommentNodeInfo; // WEAK to avoid circular ownership
|
|
|
|
mozilla::dom::NodeInfo* MOZ_NON_OWNING_REF
|
|
|
|
mDocumentNodeInfo; // WEAK to avoid circular ownership
|
2018-09-13 02:39:43 +03:00
|
|
|
NodeInfoCache mRecentlyUsedNodeInfos;
|
2019-07-10 00:19:41 +03:00
|
|
|
mozilla::Maybe<bool> mSVGEnabled; // Lazily initialized.
|
|
|
|
mozilla::Maybe<bool> mMathMLEnabled; // Lazily initialized.
|
2020-03-17 17:52:37 +03:00
|
|
|
|
|
|
|
// For dom_arena_allocator_enabled
|
|
|
|
RefPtr<mozilla::dom::DOMArena> mArena;
|
|
|
|
bool mHasAllocated = false;
|
2000-05-08 18:29:44 +04:00
|
|
|
};
|
|
|
|
|
|
|
|
#endif /* nsNodeInfoManager_h___ */
|