Bug 1351904 - Switch layout over to ArenaAllocator. r=xidorn

This switches over layout's usage of PLArena to ArenaAllocator. This allows
us to build more files in unified sources and gets rid of various CONST masks.

MozReview-Commit-ID: Aaf3Dl2kaoz
This commit is contained in:
Eric Rahm 2017-03-31 14:06:33 -07:00
parent 5706cc683b
commit 861a58d5a4
12 changed files with 32 additions and 85 deletions

View File

@ -104,6 +104,7 @@ UNIFIED_SOURCES += [
'nsLayoutDebugger.cpp',
'nsLayoutHistoryState.cpp',
'nsLayoutUtils.cpp',
'nsPresArena.cpp',
'nsPresContext.cpp',
'nsQuoteList.cpp',
'nsStyleChangeList.cpp',
@ -136,10 +137,8 @@ else:
'nsBidi_noICU.cpp',
]
# nsPresArena.cpp needs to be built separately because it uses plarena.h.
# nsRefreshDriver.cpp needs to be built separately because of name clashes in the OS X headers
SOURCES += [
'nsPresArena.cpp',
'nsRefreshDriver.cpp',
]

View File

@ -7,16 +7,6 @@
/* arena allocation for the frame tree and closely-related objects */
// Even on 32-bit systems, we allocate objects from the frame arena
// that require 8-byte alignment. The cast to uintptr_t is needed
// because plarena isn't as careful about mask construction as it
// ought to be.
#define ALIGN_SHIFT 3
#define PL_ARENA_CONST_ALIGN_MASK ((uintptr_t(1) << ALIGN_SHIFT) - 1)
#include "plarena.h"
// plarena.h needs to be included first to make it use the above
// PL_ARENA_CONST_ALIGN_MASK in this file.
#include "nsPresArena.h"
#include "mozilla/Poison.h"
@ -29,12 +19,8 @@
using namespace mozilla;
// Size to use for PLArena block allocations.
static const size_t ARENA_PAGE_SIZE = 8192;
nsPresArena::nsPresArena()
{
PL_INIT_ARENA_POOL(&mPool, "PresArena", ARENA_PAGE_SIZE);
}
nsPresArena::~nsPresArena()
@ -52,8 +38,6 @@ nsPresArena::~nsPresArena()
}
}
#endif
PL_FinishArenaPool(&mPool);
}
/* inline */ void
@ -114,7 +98,7 @@ nsPresArena::Allocate(uint32_t aCode, size_t aSize)
MOZ_ASSERT(aSize > 0, "PresArena cannot allocate zero bytes");
// We only hand out aligned sizes
aSize = PL_ARENA_ALIGN(&mPool, aSize);
aSize = mPool.AlignedSize(aSize);
// If there is no free-list entry for this type already, we have
// to create one now, to record its size.
@ -162,11 +146,7 @@ nsPresArena::Allocate(uint32_t aCode, size_t aSize)
// Allocate a new chunk from the arena
list->mEntriesEverAllocated++;
PL_ARENA_ALLOCATE(result, &mPool, aSize);
if (!result) {
NS_ABORT_OOM(aSize);
}
return result;
return mPool.Allocate(aSize);
}
void
@ -198,7 +178,7 @@ nsPresArena::AddSizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf,
// slop in the arena itself as well as the size of objects that
// we've not measured explicitly.
size_t mallocSize = PL_SizeOfArenaPoolExcludingPool(&mPool, aMallocSizeOf);
size_t mallocSize = mPool.SizeOfExcludingThis(aMallocSizeOf);
mallocSize += mFreeLists.SizeOfExcludingThis(aMallocSizeOf);
size_t totalSizeInFreeLists = 0;

View File

@ -10,6 +10,7 @@
#ifndef nsPresArena_h___
#define nsPresArena_h___
#include "mozilla/ArenaAllocator.h"
#include "mozilla/ArenaObjectID.h"
#include "mozilla/ArenaRefPtr.h"
#include "mozilla/MemoryChecking.h" // Note: Do not remove this, needed for MOZ_HAVE_MEM_CHECKS below
@ -20,7 +21,6 @@
#include "nsHashKeys.h"
#include "nsTArray.h"
#include "nsTHashtable.h"
#include "plarena.h"
struct nsArenaMemoryStats;
@ -156,7 +156,7 @@ private:
};
nsTHashtable<FreeList> mFreeLists;
PLArenaPool mPool;
mozilla::ArenaAllocator<8192, 8> mPool;
nsDataHashtable<nsPtrHashKey<void>, mozilla::ArenaObjectID> mArenaRefPtrs;
};

View File

@ -158,6 +158,7 @@ UNIFIED_SOURCES += [
'nsIntervalSet.cpp',
'nsLeafFrame.cpp',
'nsLineBox.cpp',
'nsLineLayout.cpp',
'nsPageContentFrame.cpp',
'nsPageFrame.cpp',
'nsPlaceholderFrame.cpp',
@ -186,10 +187,8 @@ UNIFIED_SOURCES += [
'ViewportFrame.cpp',
]
# nsLineLayout.cpp needs to be built separately because it uses plarena.h.
# nsPluginFrame.cpp needs to be built separately because of name clashes in the OS X headers.
SOURCES += [
'nsLineLayout.cpp',
'nsPluginFrame.cpp',
]

View File

@ -5,9 +5,6 @@
/* state and methods used while laying out a single line of a block frame */
// This has to be defined before nsLineLayout.h is included, because
// nsLineLayout.h has a #include for plarena.h, which needs this defined:
#define PL_ARENA_CONST_ALIGN_MASK (sizeof(void*)-1)
#include "nsLineLayout.h"
#include "LayoutLogging.h"
@ -111,7 +108,6 @@ nsLineLayout::nsLineLayout(nsPresContext* aPresContext,
// spans, we do it on demand so that situations that only use a few
// frames and spans won't waste a lot of time in unneeded
// initialization.
PL_INIT_ARENA_POOL(&mArena, "nsLineLayout", 1024);
mFrameFreeList = nullptr;
mSpanFreeList = nullptr;
@ -129,8 +125,6 @@ nsLineLayout::~nsLineLayout()
MOZ_COUNT_DTOR(nsLineLayout);
NS_ASSERTION(nullptr == mRootSpan, "bad line-layout user");
PL_FinishArenaPool(&mArena);
}
// Find out if the frame has a non-null prev-in-flow, i.e., whether it
@ -386,12 +380,7 @@ nsLineLayout::NewPerSpanData()
nsLineLayout* outerLineLayout = GetOutermostLineLayout();
PerSpanData* psd = outerLineLayout->mSpanFreeList;
if (!psd) {
void *mem;
size_t sz = sizeof(PerSpanData);
PL_ARENA_ALLOCATE(mem, &outerLineLayout->mArena, sz);
if (!mem) {
NS_ABORT_OOM(sz);
}
void *mem = outerLineLayout->mArena.Allocate(sizeof(PerSpanData));
psd = reinterpret_cast<PerSpanData*>(mem);
}
else {
@ -652,12 +641,7 @@ nsLineLayout::NewPerFrameData(nsIFrame* aFrame)
nsLineLayout* outerLineLayout = GetOutermostLineLayout();
PerFrameData* pfd = outerLineLayout->mFrameFreeList;
if (!pfd) {
void *mem;
size_t sz = sizeof(PerFrameData);
PL_ARENA_ALLOCATE(mem, &outerLineLayout->mArena, sz);
if (!mem) {
NS_ABORT_OOM(sz);
}
void *mem = outerLineLayout->mArena.Allocate(sizeof(PerFrameData));
pfd = reinterpret_cast<PerFrameData*>(mem);
}
else {

View File

@ -19,10 +19,10 @@
#include "gfxTypes.h"
#include "JustificationUtils.h"
#include "mozilla/ArenaAllocator.h"
#include "mozilla/WritingModes.h"
#include "BlockReflowInput.h"
#include "nsLineBox.h"
#include "plarena.h"
class nsFloatManager;
struct nsStyleText;
@ -635,7 +635,11 @@ protected:
int32_t mSpansAllocated, mSpansFreed;
int32_t mFramesAllocated, mFramesFreed;
#endif
PLArenaPool mArena; // Per span and per frame data, 4 byte aligned
/**
* Per span and per frame data.
*/
mozilla::ArenaAllocator<1024, sizeof(void*)> mArena;
/**
* Allocate a PerFrameData from the mArena pool. The allocation is infallible.

View File

@ -922,8 +922,6 @@ nsDisplayListBuilder::nsDisplayListBuilder(nsIFrame* aReferenceFrame,
mHitTestShouldStopAtFirstOpaque(false)
{
MOZ_COUNT_CTOR(nsDisplayListBuilder);
PL_InitArenaPool(&mPool, "displayListArena", 4096,
std::max(NS_ALIGNMENT_OF(void*),NS_ALIGNMENT_OF(double))-1);
nsPresContext* pc = aReferenceFrame->PresContext();
nsIPresShell *shell = pc->PresShell();
@ -1111,7 +1109,6 @@ nsDisplayListBuilder::~nsDisplayListBuilder() {
c->DisplayItemClipChain::~DisplayItemClipChain();
}
PL_FinishArenaPool(&mPool);
MOZ_COUNT_DTOR(nsDisplayListBuilder);
}
@ -1335,12 +1332,7 @@ nsDisplayListBuilder::MarkPreserve3DFramesForDisplayList(nsIFrame* aDirtyFrame)
void*
nsDisplayListBuilder::Allocate(size_t aSize)
{
void *tmp;
PL_ARENA_ALLOCATE(tmp, &mPool, aSize);
if (!tmp) {
NS_ABORT_OOM(aSize);
}
return tmp;
return mPool.Allocate(aSize);
}
ActiveScrolledRoot*

View File

@ -13,16 +13,17 @@
#ifndef NSDISPLAYLIST_H_
#define NSDISPLAYLIST_H_
#include "mozilla/ArenaAllocator.h"
#include "mozilla/Attributes.h"
#include "mozilla/Array.h"
#include "mozilla/DebugOnly.h"
#include "mozilla/EnumSet.h"
#include "mozilla/Maybe.h"
#include "mozilla/TemplateLib.h" // mozilla::tl::Max
#include "nsCOMPtr.h"
#include "nsContainerFrame.h"
#include "nsPoint.h"
#include "nsRect.h"
#include "plarena.h"
#include "nsRegion.h"
#include "nsDisplayListInvalidation.h"
#include "nsRenderingContext.h"
@ -235,7 +236,7 @@ enum class nsDisplayListBuilderMode : uint8_t {
* This manages a display list and is passed as a parameter to
* nsIFrame::BuildDisplayList.
* It contains the parameters that don't change from frame to frame and manages
* the display list memory using a PLArena. It also establishes the reference
* the display list memory using an arena. It also establishes the reference
* coordinate system for all display list items. Some of the parameters are
* available from the prescontext/presshell, but we copy them into the builder
* for faster/more convenient access.
@ -1455,7 +1456,11 @@ private:
nsIFrame* const mReferenceFrame;
nsIFrame* mIgnoreScrollFrame;
nsDisplayLayerEventRegions* mLayerEventRegions;
PLArenaPool mPool;
static const size_t kArenaAlignment =
mozilla::tl::Max<NS_ALIGNMENT_OF(void*), NS_ALIGNMENT_OF(double)>::value;
mozilla::ArenaAllocator<4096, kArenaAlignment> mPool;
nsCOMPtr<nsISelection> mBoundingSelection;
AutoTArray<PresShellState,8> mPresShellStates;
AutoTArray<nsIFrame*,100> mFramesMarkedForDisplay;

View File

@ -187,6 +187,7 @@ UNIFIED_SOURCES += [
'nsCSSProps.cpp',
'nsCSSPseudoClasses.cpp',
'nsCSSPseudoElements.cpp',
'nsCSSRuleProcessor.cpp',
'nsCSSRules.cpp',
'nsCSSScanner.cpp',
'nsCSSValue.cpp',
@ -231,12 +232,9 @@ UNIFIED_SOURCES += [
'StyleSheet.cpp',
]
# - nsCSSRuleProcessor.cpp needs to be built separately because it uses
# plarena.h.
# - nsLayoutStylesheetCache.cpp needs to be built separately because it uses
# nsExceptionHandler.h, which includes windows.h.
SOURCES += [
'nsCSSRuleProcessor.cpp',
'nsLayoutStylesheetCache.cpp',
]

View File

@ -9,13 +9,6 @@
* matching and cascading
*/
#define PL_ARENA_CONST_ALIGN_MASK 7
// We want page-sized arenas so there's no fragmentation involved.
// Including plarena.h must come first to avoid it being included by some
// header file thereby making PL_ARENA_CONST_ALIGN_MASK ineffective.
#define NS_CASCADEENUMDATA_ARENA_BLOCK_SIZE (4096)
#include "plarena.h"
#include "nsCSSRuleProcessor.h"
#include "nsAutoPtr.h"
@ -64,6 +57,8 @@
using namespace mozilla;
using namespace mozilla::dom;
typedef ArenaAllocator<4096, 8> CascadeAllocator;
#define VISITED_PSEUDO_PREF "layout.css.visited_links_enabled"
static bool gSupportVisitedPseudo = true;
@ -3444,10 +3439,8 @@ struct PerWeightDataListItem : public RuleSelectorPair {
// Placement new to arena allocate the PerWeightDataListItem
void *operator new(size_t aSize, PLArenaPool &aArena) CPP_THROW_NEW {
void *mem;
PL_ARENA_ALLOCATE(mem, &aArena, aSize);
return mem;
void *operator new(size_t aSize, CascadeAllocator &aArena) CPP_THROW_NEW {
return aArena.Allocate(aSize, fallible);
}
PerWeightDataListItem *mNext;
@ -3521,14 +3514,10 @@ struct CascadeEnumData {
mSheetType(aSheetType),
mMustGatherDocumentRules(aMustGatherDocumentRules)
{
// Initialize our arena
PL_INIT_ARENA_POOL(&mArena, "CascadeEnumDataArena",
NS_CASCADEENUMDATA_ARENA_BLOCK_SIZE);
}
~CascadeEnumData()
{
PL_FinishArenaPool(&mArena);
}
nsPresContext* mPresContext;
@ -3540,7 +3529,8 @@ struct CascadeEnumData {
nsTArray<css::DocumentRule*>& mDocumentRules;
nsMediaQueryResultCacheKey& mCacheKey;
nsDocumentRuleResultCacheKey& mDocumentCacheKey;
PLArenaPool mArena;
// We want page-sized arenas so there's no fragmentation involved.
CascadeAllocator mArena;
// Hooray, a manual PLDHashTable since nsClassHashtable doesn't
// provide a getter that gives me a *reference* to the value.
PLDHashTable mRulesByWeight; // of PerWeightDataListItem linked lists

View File

@ -12,8 +12,7 @@ EXPORTS += [
'nsViewManager.h',
]
# nsViewManager.cpp cannot be built in unified mode because it uses PL_ARENA_CONST_ALIGN_MASK.
SOURCES += [
UNIFIED_SOURCES += [
'nsView.cpp',
'nsViewManager.cpp',
]

View File

@ -3,9 +3,6 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#define PL_ARENA_CONST_ALIGN_MASK (sizeof(void*)-1)
#include "plarena.h"
#include "nsAutoPtr.h"
#include "nsViewManager.h"
#include "nsGfxCIID.h"