summaryrefslogtreecommitdiff
path: root/Source/JavaScriptCore/heap/MarkStack.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'Source/JavaScriptCore/heap/MarkStack.cpp')
-rw-r--r--Source/JavaScriptCore/heap/MarkStack.cpp56
1 files changed, 47 insertions, 9 deletions
diff --git a/Source/JavaScriptCore/heap/MarkStack.cpp b/Source/JavaScriptCore/heap/MarkStack.cpp
index cf6e3513c..785444e55 100644
--- a/Source/JavaScriptCore/heap/MarkStack.cpp
+++ b/Source/JavaScriptCore/heap/MarkStack.cpp
@@ -36,6 +36,7 @@
#include "JSObject.h"
#include "ScopeChain.h"
#include "Structure.h"
+#include "UString.h"
#include "WriteBarrier.h"
#include <wtf/MainThread.h>
@@ -218,17 +219,24 @@ void MarkStackArray::stealSomeCellsFrom(MarkStackArray& other)
}
#if ENABLE(PARALLEL_GC)
-void MarkStackThreadSharedData::markingThreadMain()
+void MarkStackThreadSharedData::resetChildren()
+{
+ for (unsigned i = 0; i < m_slaveMarkStacks.size(); ++i)
+ m_slaveMarkStacks[i]->reset();
+}
+
+void MarkStackThreadSharedData::markingThreadMain(SlotVisitor* slotVisitor)
{
WTF::registerGCThread();
- SlotVisitor slotVisitor(*this);
- ParallelModeEnabler enabler(slotVisitor);
- slotVisitor.drainFromShared(SlotVisitor::SlaveDrain);
+ ParallelModeEnabler enabler(*slotVisitor);
+ slotVisitor->drainFromShared(SlotVisitor::SlaveDrain);
+ delete slotVisitor;
}
-void MarkStackThreadSharedData::markingThreadStartFunc(void* shared)
+void MarkStackThreadSharedData::markingThreadStartFunc(void* myVisitor)
{
- static_cast<MarkStackThreadSharedData*>(shared)->markingThreadMain();
+ SlotVisitor* slotVisitor = static_cast<SlotVisitor*>(myVisitor);
+ slotVisitor->sharedData().markingThreadMain(slotVisitor);
}
#endif
@@ -241,7 +249,9 @@ MarkStackThreadSharedData::MarkStackThreadSharedData(JSGlobalData* globalData)
{
#if ENABLE(PARALLEL_GC)
for (unsigned i = 1; i < Options::numberOfGCMarkers; ++i) {
- m_markingThreads.append(createThread(markingThreadStartFunc, this, "JavaScriptCore::Marking"));
+ SlotVisitor* slotVisitor = new SlotVisitor(*this);
+ m_slaveMarkStacks.append(slotVisitor);
+ m_markingThreads.append(createThread(markingThreadStartFunc, slotVisitor, "JavaScriptCore::Marking"));
ASSERT(m_markingThreads.last());
}
#endif
@@ -273,7 +283,6 @@ void MarkStackThreadSharedData::reset()
#else
ASSERT(m_opaqueRoots.isEmpty());
#endif
-
m_weakReferenceHarvesters.removeAll();
}
@@ -286,6 +295,7 @@ void MarkStack::reset()
#else
m_opaqueRoots.clear();
#endif
+ m_uniqueStrings.clear();
}
void MarkStack::append(ConservativeRoots& conservativeRoots)
@@ -486,6 +496,34 @@ void* SlotVisitor::allocateNewSpace(void* ptr, size_t bytes)
return CopiedSpace::allocateFromBlock(m_copyBlock, bytes);
}
+inline void MarkStack::internalAppend(JSValue* slot)
+{
+ ASSERT(slot);
+ JSValue value = *slot;
+ ASSERT(value);
+ if (!value.isCell())
+ return;
+
+ if (value.isString()) {
+ JSString* string = jsCast<JSString*>(value.asCell());
+ if (!string->isHashConstSingleton() && string->length() > 1 && !string->isRope()) {
+ UniqueStringMap::AddResult addResult = m_uniqueStrings.add(string->string().impl(), value);
+ if (addResult.isNewEntry)
+ string->setHashConstSingleton();
+ else {
+ JSValue existingJSValue = addResult.iterator->second;
+ if (value != existingJSValue)
+ jsCast<JSString*>(existingJSValue.asCell())->clearHashConstSingleton();
+ *slot = existingJSValue;
+ return;
+ }
+ }
+ }
+
+ internalAppend(value.asCell());
+}
+
+
void SlotVisitor::copyAndAppend(void** ptr, size_t bytes, JSValue* values, unsigned length)
{
void* oldPtr = *ptr;
@@ -499,7 +537,7 @@ void SlotVisitor::copyAndAppend(void** ptr, size_t bytes, JSValue* values, unsig
newValues[i] = value;
if (!value)
continue;
- internalAppend(value);
+ internalAppend(&newValues[i]);
}
memcpy(newPtr, oldPtr, jsValuesOffset);