add main thread only cache for nsIAtoms to speed up atomization xpcom/ds

add main thread only cache for nsIAtoms to speed up atomization
This commit is contained in:
win7-7
2019-05-24 13:58:13 +03:00
committed by GitHub
parent a3434ba005
commit ddff63b2d6
2 changed files with 57 additions and 2 deletions
+52 -2
View File
@@ -364,17 +364,31 @@ static const PLDHashTableOps AtomTableOps = {
//----------------------------------------------------------------------
#define RECENTLY_USED_MAIN_THREAD_ATOM_CACHE_SIZE 31
static nsIAtom*
sRecentlyUsedMainThreadAtoms[RECENTLY_USED_MAIN_THREAD_ATOM_CACHE_SIZE] = {};
void
DynamicAtom::GCAtomTable()
{
MutexAutoLock lock(*gAtomTableLock);
GCAtomTableLocked(lock, GCKind::RegularOperation);
if (NS_IsMainThread()) {
MutexAutoLock lock(*gAtomTableLock);
GCAtomTableLocked(lock, GCKind::RegularOperation);
}
}
void
DynamicAtom::GCAtomTableLocked(const MutexAutoLock& aProofOfLock,
GCKind aKind)
{
MOZ_ASSERT(NS_IsMainThread());
for (uint32_t i = 0; i < RECENTLY_USED_MAIN_THREAD_ATOM_CACHE_SIZE; ++i) {
sRecentlyUsedMainThreadAtoms[i] = nullptr;
}
uint32_t removedCount = 0; // Use a non-atomic temporary for cheaper increments.
nsAutoCString nonZeroRefcountAtoms;
uint32_t nonZeroRefcountAtomsCount = 0;
@@ -673,6 +687,8 @@ NS_Atomize(const nsACString& aUTF8String)
return atom.forget();
}
// This results in an extra addref/release of the nsStringBuffer.
// Unfortunately there doesn't seem to be any APIs to avoid that.
// Actually, now there is, sort of: ForgetSharedBuffer.
@@ -712,6 +728,40 @@ NS_Atomize(const nsAString& aUTF16String)
return atom.forget();
}
already_AddRefed<nsIAtom>
NS_AtomizeMainThread(const nsAString& aUTF16String)
{
MOZ_ASSERT(NS_IsMainThread());
nsCOMPtr<nsIAtom> retVal;
uint32_t hash;
AtomTableKey key(aUTF16String.Data(), aUTF16String.Length(), &hash);
uint32_t index = hash % RECENTLY_USED_MAIN_THREAD_ATOM_CACHE_SIZE;
nsIAtom* atom =
sRecentlyUsedMainThreadAtoms[index];
if (atom) {
uint32_t length = atom->GetLength();
if (length == key.mLength &&
(memcmp(atom->GetUTF16String(),
key.mUTF16String, length * sizeof(char16_t)) == 0)) {
retVal = atom;
return retVal.forget();
}
}
MutexAutoLock lock(*gAtomTableLock);
AtomTableEntry* he = static_cast<AtomTableEntry*>(gAtomTable->Add(&key));
if (he->mAtom) {
retVal = he->mAtom;
} else {
retVal = DynamicAtom::Create(aUTF16String, hash);
he->mAtom = retVal;
}
sRecentlyUsedMainThreadAtoms[index] = retVal;
return retVal.forget();
}
nsrefcnt
NS_GetNumberOfAtoms(void)
{
+5
View File
@@ -119,6 +119,11 @@ extern already_AddRefed<nsIAtom> NS_Atomize(const char16_t* aUTF16String);
*/
extern already_AddRefed<nsIAtom> NS_Atomize(const nsAString& aUTF16String);
/**
* An optimized version of the method above for the main thread.
*/
extern already_AddRefed<nsIAtom> NS_AtomizeMainThread(const nsAString& aUTF16String);
/**
* Return a count of the total number of atoms currently
* alive in the system.