2011-05-25 Oliver Hunt <oliver@apple.com>
authoroliver@apple.com <oliver@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 26 May 2011 01:12:46 +0000 (01:12 +0000)
committeroliver@apple.com <oliver@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 26 May 2011 01:12:46 +0000 (01:12 +0000)
        Reviewed by Geoffrey Garen.

        Make RegExp GC allocated
        https://bugs.webkit.org/show_bug.cgi?id=61490

        Make RegExp GC allocated.  Basically mechanical change to replace
        most use of [Pass]RefPtr<RegExp> with RegExp* or WriteBarrier<RegExp>
        where actual ownership happens.

        Made the RegExpCache use Strong<> references currently to avoid any
        changes in behaviour.

        * JavaScriptCore.exp:
        * bytecode/CodeBlock.cpp:
        (JSC::CodeBlock::visitAggregate):
        * bytecode/CodeBlock.h:
        (JSC::CodeBlock::addRegExp):
        * bytecompiler/BytecodeGenerator.cpp:
        (JSC::BytecodeGenerator::addRegExp):
        (JSC::BytecodeGenerator::emitNewRegExp):
        * bytecompiler/BytecodeGenerator.h:
        * runtime/JSCell.h:
        * runtime/JSGlobalData.cpp:
        (JSC::JSGlobalData::JSGlobalData):
        (JSC::JSGlobalData::clearBuiltinStructures):
        (JSC::JSGlobalData::addRegExpToTrace):
        * runtime/JSGlobalData.h:
        * runtime/JSGlobalObject.cpp:
        (JSC::JSGlobalObject::reset):
        * runtime/RegExp.cpp:
        (JSC::RegExp::RegExp):
        (JSC::RegExp::create):
        (JSC::RegExp::invalidateCode):
        * runtime/RegExp.h:
        (JSC::RegExp::createStructure):
        * runtime/RegExpCache.cpp:
        (JSC::RegExpCache::lookupOrCreate):
        (JSC::RegExpCache::create):
        * runtime/RegExpCache.h:
        * runtime/RegExpConstructor.cpp:
        (JSC::constructRegExp):
        * runtime/RegExpObject.cpp:
        (JSC::RegExpObject::RegExpObject):
        (JSC::RegExpObject::visitChildren):
        * runtime/RegExpObject.h:
        (JSC::RegExpObject::setRegExp):
        (JSC::RegExpObject::RegExpObjectData::RegExpObjectData):
        * runtime/RegExpPrototype.cpp:
        (JSC::RegExpPrototype::RegExpPrototype):
        (JSC::regExpProtoFuncCompile):
        * runtime/RegExpPrototype.h:
        * runtime/StringPrototype.cpp:
        (JSC::stringProtoFuncMatch):
        (JSC::stringProtoFuncSearch):
2011-05-25  James Robinson  <jamesr@chromium.org>

        Reviewed by Geoffrey Garen

        CachedResource overhead size calculation ignores the actual size of the URL
        https://bugs.webkit.org/show_bug.cgi?id=61481

        CachedResource::overheadSize is used to determine the size of an entry in the memory cache to know when to evict
        it.  When the resource is a large data: URL, for example representing image or audio data, the URL size itself
        can be significant.

        This patch uses an estimate of actual number of bytes used by the URL that is valid for ASCII urls and close for
        other types of strings instead of a fixed number.

        * loader/cache/CachedResource.cpp:
        (WebCore::CachedResource::overheadSize):

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@87346 268f45cc-cd09-0410-ab3c-d52691b4dbfc

24 files changed:
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/JavaScriptCore.exp
Source/JavaScriptCore/JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.def
Source/JavaScriptCore/bytecode/CodeBlock.cpp
Source/JavaScriptCore/bytecode/CodeBlock.h
Source/JavaScriptCore/bytecompiler/BytecodeGenerator.cpp
Source/JavaScriptCore/bytecompiler/BytecodeGenerator.h
Source/JavaScriptCore/runtime/JSCell.h
Source/JavaScriptCore/runtime/JSGlobalData.cpp
Source/JavaScriptCore/runtime/JSGlobalData.h
Source/JavaScriptCore/runtime/JSGlobalObject.cpp
Source/JavaScriptCore/runtime/RegExp.cpp
Source/JavaScriptCore/runtime/RegExp.h
Source/JavaScriptCore/runtime/RegExpCache.cpp
Source/JavaScriptCore/runtime/RegExpCache.h
Source/JavaScriptCore/runtime/RegExpConstructor.cpp
Source/JavaScriptCore/runtime/RegExpObject.cpp
Source/JavaScriptCore/runtime/RegExpObject.h
Source/JavaScriptCore/runtime/RegExpPrototype.cpp
Source/JavaScriptCore/runtime/RegExpPrototype.h
Source/JavaScriptCore/runtime/StringPrototype.cpp
Source/WebCore/ChangeLog
Source/WebCore/bindings/js/SerializedScriptValue.cpp
Source/WebCore/bridge/qt/qt_runtime.cpp

index 1936ebb610e5938b27de54d1471abfd4493855e8..27f6edcf041fa6ef3e31598e3c73f2caab181155 100644 (file)
@@ -1,7 +1,3 @@
-2011-05-25  Oliver Hunt  <oliver@apple.com>
-
-        Revert last change, something weird happened when I went to land.
-
 2011-05-25  Oliver Hunt  <oliver@apple.com>
 
         Reviewed by Geoffrey Garen.
index fb370fbd8cc05ba3c2d5eaf38a1d1327d458fbe8..6d6ced2bed48f4deb76861ba4a02495c597b3094 100644 (file)
@@ -137,7 +137,7 @@ __ZN3JSC12JSGlobalData22clearBuiltinStructuresEv
 __ZN3JSC12JSGlobalData6createENS_15ThreadStackTypeE
 __ZN3JSC12JSGlobalDataD1Ev
 __ZN3JSC12RegExpObject6s_infoE
-__ZN3JSC12RegExpObjectC1EPNS_14JSGlobalObjectEPNS_9StructureEN3WTF17NonNullPassRefPtrINS_6RegExpEEE
+__ZN3JSC12RegExpObjectC1EPNS_14JSGlobalObjectEPNS_9StructureEPNS_6RegExpE
 __ZN3JSC12SamplingTool5setupEv
 __ZN3JSC12SmallStrings17createEmptyStringEPNS_12JSGlobalDataE
 __ZN3JSC12SmallStrings27createSingleCharacterStringEPNS_12JSGlobalDataEh
index 908e8a1117bdf7ae91814518baec99af40a6d3e2..6225da78084553a183ad08b85479a10e0fc675b0 100644 (file)
@@ -18,7 +18,7 @@ EXPORTS
     ??0MD5@WTF@@QAE@XZ
     ??0Mutex@WTF@@QAE@XZ
     ??0RefCountedLeakCounter@WTF@@QAE@PBD@Z
-    ??0RegExpObject@JSC@@QAE@PAVJSGlobalObject@1@PAVStructure@1@V?$NonNullPassRefPtr@VRegExp@JSC@@@WTF@@@Z
+    ??0RegExpObject@JSC@@QAE@PAVJSGlobalObject@1@PAVStructure@1@PAVRegExp@1@JSC@@@WTF@@@Z
     ??0SHA1@WTF@@QAE@XZ
     ??0StringObject@JSC@@QAE@PAVExecState@1@PAVStructure@1@ABVUString@1@@Z
     ??0Structure@JSC@@AAE@AAVJSGlobalData@1@VJSValue@1@ABVTypeInfo@1@IPBUClassInfo@1@@Z
index 6a0c87951d3702c824ddd815d94a9a09bf16f706..da4ca45c16e33846617b637c628fd95e9d53ebe8 100644 (file)
@@ -1470,8 +1470,13 @@ void CodeBlock::visitAggregate(SlotVisitor& visitor)
 {
     visitor.append(&m_globalObject);
     visitor.append(&m_ownerExecutable);
-    if (m_rareData)
+    if (m_rareData) {
         m_rareData->m_evalCodeCache.visitAggregate(visitor);
+        size_t regExpCount = m_rareData->m_regexps.size();
+        WriteBarrier<RegExp>* regexps = m_rareData->m_regexps.data();
+        for (size_t i = 0; i < regExpCount; i++)
+            visitor.append(regexps + i);
+    }
     visitor.appendValues(m_constantRegisters.data(), m_constantRegisters.size());
     for (size_t i = 0; i < m_functionExprs.size(); ++i)
         visitor.append(&m_functionExprs[i]);
index 33e39c535cc4517b92bb5e95e493d4f7e051aca7..ce18f09077a83d2f1cec411b376604daa583489d 100644 (file)
@@ -36,7 +36,7 @@
 #include "JSGlobalObject.h"
 #include "JumpTable.h"
 #include "Nodes.h"
-#include "RegExp.h"
+#include "RegExpObject.h"
 #include "UString.h"
 #include <wtf/FastAllocBase.h>
 #include <wtf/PassOwnPtr.h>
@@ -451,7 +451,13 @@ namespace JSC {
         }
         FunctionExecutable* functionExpr(int index) { return m_functionExprs[index].get(); }
 
-        unsigned addRegExp(PassRefPtr<RegExp> r) { createRareDataIfNecessary(); unsigned size = m_rareData->m_regexps.size(); m_rareData->m_regexps.append(r); return size; }
+        unsigned addRegExp(RegExp* r)
+        {
+            createRareDataIfNecessary();
+            unsigned size = m_rareData->m_regexps.size();
+            m_rareData->m_regexps.append(WriteBarrier<RegExp>(*m_globalData, ownerExecutable(), r));
+            return size;
+        }
         RegExp* regexp(int index) const { ASSERT(m_rareData); return m_rareData->m_regexps[index].get(); }
 
         JSGlobalObject* globalObject() { return m_globalObject.get(); }
@@ -555,7 +561,7 @@ namespace JSC {
             Vector<HandlerInfo> m_exceptionHandlers;
 
             // Rare Constants
-            Vector<RefPtr<RegExp> > m_regexps;
+            Vector<WriteBarrier<RegExp> > m_regexps;
 
             // Jump Tables
             Vector<SimpleJumpTable> m_immediateSwitchJumpTables;
index 1c126de71c4299a8da8814394ea9913bca1f08b4..064df2dd5d98accc782c7cca58a291681cc1976c 100644 (file)
@@ -966,7 +966,7 @@ RegisterID* BytecodeGenerator::addConstantValue(JSValue v)
     return &m_constantPoolRegisters[index];
 }
 
-unsigned BytecodeGenerator::addRegExp(PassRefPtr<RegExp> r)
+unsigned BytecodeGenerator::addRegExp(RegExp* r)
 {
     return m_codeBlock->addRegExp(r);
 }
@@ -1592,7 +1592,7 @@ RegisterID* BytecodeGenerator::emitNewFunctionInternal(RegisterID* dst, unsigned
     return dst;
 }
 
-RegisterID* BytecodeGenerator::emitNewRegExp(RegisterID* dst, PassRefPtr<RegExp> regExp)
+RegisterID* BytecodeGenerator::emitNewRegExp(RegisterID* dst, RegExp* regExp)
 {
     emitOpcode(op_new_regexp);
     instructions().append(dst->index());
index 812b1012df6dac77d451d71fba224ce239af0db7..b1230e61a50dec2f28d12fbd4fa909f110d280d6 100644 (file)
@@ -291,7 +291,7 @@ namespace JSC {
         RegisterID* emitLazyNewFunction(RegisterID* dst, FunctionBodyNode* body);
         RegisterID* emitNewFunctionInternal(RegisterID* dst, unsigned index, bool shouldNullCheck);
         RegisterID* emitNewFunctionExpression(RegisterID* dst, FuncExprNode* func);
-        RegisterID* emitNewRegExp(RegisterID* dst, PassRefPtr<RegExp> regExp);
+        RegisterID* emitNewRegExp(RegisterID* dst, RegExp*);
 
         RegisterID* emitMove(RegisterID* dst, RegisterID* src);
 
@@ -475,7 +475,7 @@ namespace JSC {
 
         unsigned addConstant(const Identifier&);
         RegisterID* addConstantValue(JSValue);
-        unsigned addRegExp(PassRefPtr<RegExp>);
+        unsigned addRegExp(RegExp*);
 
         FunctionExecutable* makeFunction(ExecState* exec, FunctionBodyNode* body)
         {
index 9595fdd0943c02e42ed651f41e92c6fec962e46a..3fbc4dfbda27deb02414c0f9d92564251e905032 100644 (file)
@@ -71,6 +71,7 @@ namespace JSC {
         friend class ScopeChainNode;
         friend class Structure;
         friend class StructureChain;
+        friend class RegExp;
         enum CreatingEarlyCellTag { CreatingEarlyCell };
 
     protected:
index 66d61530395cf9608112c4629bf49968608f4b4c..50ad5581f90e8b20b47a4089713c536437b10a53 100644 (file)
@@ -52,6 +52,7 @@
 #include "Nodes.h"
 #include "Parser.h"
 #include "RegExpCache.h"
+#include "RegExpObject.h"
 #include "StrictEvalActivation.h"
 #include <wtf/WTFThreadData.h>
 #if ENABLE(REGEXP_TRACING)
@@ -219,6 +220,7 @@ JSGlobalData::JSGlobalData(GlobalDataType globalDataType, ThreadStackType thread
     programExecutableStructure.set(*this, ProgramExecutable::createStructure(*this, jsNull()));
     functionExecutableStructure.set(*this, FunctionExecutable::createStructure(*this, jsNull()));
     dummyMarkableCellStructure.set(*this, JSCell::createDummyStructure(*this));
+    regExpStructure.set(*this, RegExp::createStructure(*this, jsNull()));
     structureChainStructure.set(*this, StructureChain::createStructure(*this, jsNull()));
 
 #if ENABLE(JSC_ZOMBIES)
@@ -279,8 +281,9 @@ void JSGlobalData::clearBuiltinStructures()
     programExecutableStructure.clear();
     functionExecutableStructure.clear();
     dummyMarkableCellStructure.clear();
+    regExpStructure.clear();
     structureChainStructure.clear();
-    
+
 #if ENABLE(JSC_ZOMBIES)
     zombieStructure.clear();
 #endif
@@ -446,7 +449,7 @@ void JSGlobalData::recompileAllJSFunctions()
 }
 
 #if ENABLE(REGEXP_TRACING)
-void JSGlobalData::addRegExpToTrace(PassRefPtr<RegExp> regExp)
+void JSGlobalData::addRegExpToTrace(RegExp* regExp)
 {
     m_rtTraceList->add(regExp);
 }
index 7bf7806fd3e3e0aa7b2bfb34a9abef6564f07b80..af538362da30a4bbb29f4278b31ea581d6d24af0 100644 (file)
@@ -174,6 +174,7 @@ namespace JSC {
         Strong<Structure> programExecutableStructure;
         Strong<Structure> functionExecutableStructure;
         Strong<Structure> dummyMarkableCellStructure;
+        Strong<Structure> regExpStructure;
         Strong<Structure> structureChainStructure;
 
 #if ENABLE(JSC_ZOMBIES)
index 3e7fcfea29a422a74961c676cd98d01805982303..4bb20aa735f821d0c6252f9041d1ac96231bbc44 100644 (file)
@@ -222,7 +222,9 @@ void JSGlobalObject::reset(JSValue prototype)
     m_datePrototype.set(exec->globalData(), this, new (exec) DatePrototype(exec, this, DatePrototype::createStructure(exec->globalData(), m_objectPrototype.get())));
     m_dateStructure.set(exec->globalData(), this, DateInstance::createStructure(exec->globalData(), m_datePrototype.get()));
 
-    m_regExpPrototype.set(exec->globalData(), this, new (exec) RegExpPrototype(exec, this, RegExpPrototype::createStructure(exec->globalData(), m_objectPrototype.get())));
+    RegExp* emptyRegex = RegExp::create(&exec->globalData(), "", NoFlags);
+    
+    m_regExpPrototype.set(exec->globalData(), this, new (exec) RegExpPrototype(exec, this, RegExpPrototype::createStructure(exec->globalData(), m_objectPrototype.get()), emptyRegex));
     m_regExpStructure.set(exec->globalData(), this, RegExpObject::createStructure(exec->globalData(), m_regExpPrototype.get()));
 
     m_methodCallDummy.set(exec->globalData(), this, constructEmptyObject(exec));
index fd31cdfee2e98ea15b3dbd2e73b1b6b9d642eea0..cb667b25e9f42932014950b9e4b6457f7262ac50 100644 (file)
@@ -34,6 +34,8 @@
 
 namespace JSC {
 
+const ClassInfo RegExp::s_info = { "RegExp", 0, 0, 0 };
+
 RegExpFlags regExpFlags(const UString& string)
 {
     RegExpFlags flags = NoFlags;
@@ -73,8 +75,9 @@ struct RegExpRepresentation {
     OwnPtr<Yarr::BytecodePattern> m_regExpBytecode;
 };
 
-inline RegExp::RegExp(JSGlobalData*, const UString& patternString, RegExpFlags flags)
-    : m_state(NotCompiled)
+inline RegExp::RegExp(JSGlobalData* globalData, const UString& patternString, RegExpFlags flags)
+    : JSCell(*globalData, globalData->regExpStructure.get())
+    , m_state(NotCompiled)
     , m_patternString(patternString)
     , m_flags(flags)
     , m_constructionError(0)
@@ -95,13 +98,13 @@ RegExp::~RegExp()
 {
 }
 
-PassRefPtr<RegExp> RegExp::create(JSGlobalData* globalData, const UString& patternString, RegExpFlags flags)
+RegExp* RegExp::create(JSGlobalData* globalData, const UString& patternString, RegExpFlags flags)
 {
-    RefPtr<RegExp> res = adoptRef(new RegExp(globalData, patternString, flags));
+    RegExp* res = new (globalData) RegExp(globalData, patternString, flags);
 #if ENABLE(REGEXP_TRACING)
     globalData->addRegExpToTrace(res);
 #endif
-    return res.release();
+    return res;
 }
 
 void RegExp::compile(JSGlobalData* globalData)
@@ -194,6 +197,10 @@ int RegExp::match(JSGlobalData& globalData, const UString& s, int startOffset, V
     return -1;
 }
 
+void RegExp::invalidateCode()
+{
+    m_representation.clear();
+}
 
 #if ENABLE(YARR_JIT_DEBUG)
 void RegExp::matchCompareWithInterpreter(const UString& s, int startOffset, int* offsetVector, int jitResult)
index 997a42ffd93cb4c4d04ea290035bae40af7d1c05..0b3a235efb1388779e85d0d6798c746dd24d0d05 100644 (file)
@@ -24,6 +24,7 @@
 
 #include "UString.h"
 #include "ExecutableAllocator.h"
+#include "Structure.h"
 #include "RegExpKey.h"
 #include <wtf/Forward.h>
 #include <wtf/RefCounted.h>
@@ -35,9 +36,9 @@ namespace JSC {
 
     RegExpFlags regExpFlags(const UString&);
 
-    class RegExp : public RefCounted<RegExp> {
+    class RegExp : public JSCell {
     public:
-        static PassRefPtr<RegExp> create(JSGlobalData* globalData, const UString& pattern, RegExpFlags);
+        static RegExp* create(JSGlobalData*, const UString& pattern, RegExpFlags);
         ~RegExp();
 
         bool global() const { return m_flags & FlagGlobal; }
@@ -52,10 +53,19 @@ namespace JSC {
         int match(JSGlobalData&, const UString&, int startOffset, Vector<int, 32>* ovector = 0);
         unsigned numSubpatterns() const { return m_numSubpatterns; }
         
+        void invalidateCode();
+        
 #if ENABLE(REGEXP_TRACING)
         void printTraceData();
 #endif
 
+        static Structure* createStructure(JSGlobalData& globalData, JSValue prototype)
+        {
+            return Structure::create(globalData, prototype, TypeInfo(LeafType, 0), 0, &s_info);
+        }
+        
+        static JS_EXPORTDATA const ClassInfo s_info;
+        
     private:
         RegExp(JSGlobalData* globalData, const UString& pattern, RegExpFlags);
 
index c96b04720e9d2598aca73db4a92063b60ccd7c58..67e013fdea1aa30b5e6da4b5a7bdd01b9fda119e 100644 (file)
 #include "config.h"
 
 #include "RegExpCache.h"
+#include "RegExpObject.h"
 
 namespace JSC {
 
-PassRefPtr<RegExp> RegExpCache::lookupOrCreate(const UString& patternString, RegExpFlags flags)
+RegExp* RegExpCache::lookupOrCreate(const UString& patternString, RegExpFlags flags)
 {
     if (patternString.length() < maxCacheablePatternLength) {
-        pair<RegExpCacheMap::iterator, bool> result = m_cacheMap.add(RegExpKey(flags, patternString), 0);
+        pair<RegExpCacheMap::iterator, bool> result = m_cacheMap.add(RegExpKey(flags, patternString), Strong<RegExp>());
         if (!result.second)
-            return result.first->second;
+            return result.first->second.get();
         else
             return create(patternString, flags, result.first);
     }
     return create(patternString, flags, m_cacheMap.end());
 }
 
-PassRefPtr<RegExp> RegExpCache::create(const UString& patternString, RegExpFlags flags, RegExpCacheMap::iterator iterator) 
+RegExp* RegExpCache::create(const UString& patternString, RegExpFlags flags, RegExpCacheMap::iterator iterator) 
 {
-    RefPtr<RegExp> regExp = RegExp::create(m_globalData, patternString, flags);
-
+    RegExp* regExp = RegExp::create(m_globalData, patternString, flags);
     if (patternString.length() >= maxCacheablePatternLength)
         return regExp;
 
     RegExpKey key = RegExpKey(flags, patternString);
     iterator->first = key;
-    iterator->second = regExp;
+    iterator->second.set(*m_globalData, regExp);
 
     ++m_nextKeyToEvict;
     if (m_nextKeyToEvict == maxCacheableEntries) {
index b4a6ae522c05fa888c6df8bb43d67d2f9217088b..3ef6b709f94572ec00759c884eb5450f3ea4018b 100644 (file)
@@ -27,6 +27,7 @@
 
 #include "RegExp.h"
 #include "RegExpKey.h"
+#include "Strong.h"
 #include "UString.h"
 #include <wtf/FixedArray.h>
 #include <wtf/HashMap.h>
@@ -38,11 +39,11 @@ namespace JSC {
 
 class RegExpCache {
 
-typedef HashMap<RegExpKey, RefPtr<RegExp> > RegExpCacheMap;
+typedef HashMap<RegExpKey, Strong<RegExp> > RegExpCacheMap;
 
 public:
-    PassRefPtr<RegExp> lookupOrCreate(const UString& patternString, RegExpFlags);
-    PassRefPtr<RegExp> create(const UString& patternString, RegExpFlags, RegExpCacheMap::iterator);
+    RegExp* lookupOrCreate(const UString& patternString, RegExpFlags);
+    RegExp* create(const UString& patternString, RegExpFlags, RegExpCacheMap::iterator);
     RegExpCache(JSGlobalData* globalData);
 
 private:
index 3da01981cbe873ee978e426fb902042abf76483c..bc0b5737688dbb86c68e9c14d4402b07753f0146 100644 (file)
@@ -317,10 +317,10 @@ JSObject* constructRegExp(ExecState* exec, JSGlobalObject* globalObject, const A
             return throwError(exec, createSyntaxError(exec, "Invalid flags supplied to RegExp constructor."));
     }
 
-    RefPtr<RegExp> regExp = exec->globalData().regExpCache()->lookupOrCreate(pattern, flags);
+    RegExp* regExp = exec->globalData().regExpCache()->lookupOrCreate(pattern, flags);
     if (!regExp->isValid())
         return throwError(exec, createSyntaxError(exec, regExp->errorMessage()));
-    return new (exec) RegExpObject(exec->lexicalGlobalObject(), globalObject->regExpStructure(), regExp.release());
+    return new (exec) RegExpObject(exec->lexicalGlobalObject(), globalObject->regExpStructure(), regExp);
 }
 
 static EncodedJSValue JSC_HOST_CALL constructWithRegExpConstructor(ExecState* exec)
index be12fea18d985e4137398b96eee142bfba7590e0..83e7c5a7573a4ff9d10c64aa653cc8b88424cbf1 100644 (file)
@@ -61,9 +61,9 @@ const ClassInfo RegExpObject::s_info = { "RegExp", &JSObjectWithGlobalObject::s_
 @end
 */
 
-RegExpObject::RegExpObject(JSGlobalObject* globalObject, Structure* structure, NonNullPassRefPtr<RegExp> regExp)
+RegExpObject::RegExpObject(JSGlobalObject* globalObject, Structure* structure, RegExp* regExp)
     : JSObjectWithGlobalObject(globalObject, structure)
-    , d(adoptPtr(new RegExpObjectData(regExp)))
+    , d(adoptPtr(new RegExpObjectData(globalObject->globalData(), this, regExp)))
 {
     ASSERT(inherits(&s_info));
 }
@@ -78,6 +78,8 @@ void RegExpObject::visitChildren(SlotVisitor& visitor)
     COMPILE_ASSERT(StructureFlags & OverridesVisitChildren, OverridesVisitChildrenWithoutSettingFlag);
     ASSERT(structure()->typeInfo().overridesVisitChildren());
     Base::visitChildren(visitor);
+    if (d->regExp)
+        visitor.append(&d->regExp);
     if (UNLIKELY(!d->lastIndex.get().isInt32()))
         visitor.append(&d->lastIndex);
 }
index a0803ebdad1f266cab90dd13a96eaced167562b9..6fc6cb9a72f298527c3a654ef55b8248e7eb0740 100644 (file)
 #include "RegExp.h"
 
 namespace JSC {
-
+    
     class RegExpObject : public JSObjectWithGlobalObject {
     public:
         typedef JSObjectWithGlobalObject Base;
 
-        RegExpObject(JSGlobalObject*, Structure*, NonNullPassRefPtr<RegExp>);
+        RegExpObject(JSGlobalObject*, Structure*, RegExp*);
         virtual ~RegExpObject();
 
-        void setRegExp(PassRefPtr<RegExp> r) { d->regExp = r; }
+        void setRegExp(JSGlobalData& globalData, RegExp* r) { d->regExp.set(globalData, this, r); }
         RegExp* regExp() const { return d->regExp.get(); }
 
         void setLastIndex(size_t lastIndex)
@@ -74,13 +74,13 @@ namespace JSC {
         struct RegExpObjectData {
             WTF_MAKE_FAST_ALLOCATED;
         public:
-            RegExpObjectData(NonNullPassRefPtr<RegExp> regExp)
-                : regExp(regExp)
+            RegExpObjectData(JSGlobalData& globalData, RegExpObject* owner, RegExp* regExp)
+                : regExp(globalData, owner, regExp)
             {
                 lastIndex.setWithoutWriteBarrier(jsNumber(0));
             }
 
-            RefPtr<RegExp> regExp;
+            WriteBarrier<RegExp> regExp;
             WriteBarrier<Unknown> lastIndex;
         };
 #if COMPILER(MSVC)
index 20bb6e066a004d599eebbc51c92d8d642336340f..a31f1cf1fd39841f418e9c5da223042bf2f6a7d0 100644 (file)
@@ -62,8 +62,8 @@ const ClassInfo RegExpPrototype::s_info = { "RegExp", &RegExpObject::s_info, 0,
 
 ASSERT_CLASS_FITS_IN_CELL(RegExpPrototype);
 
-RegExpPrototype::RegExpPrototype(ExecState* exec, JSGlobalObject* globalObject, Structure* structure)
-    : RegExpObject(globalObject, structure, RegExp::create(&exec->globalData(), "", NoFlags))
+RegExpPrototype::RegExpPrototype(ExecState*, JSGlobalObject* globalObject, Structure* structure, RegExp* regExp)
+    : RegExpObject(globalObject, structure, regExp)
 {
 }
 
@@ -101,7 +101,7 @@ EncodedJSValue JSC_HOST_CALL regExpProtoFuncCompile(ExecState* exec)
     if (!thisValue.inherits(&RegExpObject::s_info))
         return throwVMTypeError(exec);
 
-    RefPtr<RegExp> regExp;
+    RegExp* regExp;
     JSValue arg0 = exec->argument(0);
     JSValue arg1 = exec->argument(1);
     
@@ -128,7 +128,7 @@ EncodedJSValue JSC_HOST_CALL regExpProtoFuncCompile(ExecState* exec)
     if (!regExp->isValid())
         return throwVMError(exec, createSyntaxError(exec, regExp->errorMessage()));
 
-    asRegExpObject(thisValue)->setRegExp(regExp.release());
+    asRegExpObject(thisValue)->setRegExp(exec->globalData(), regExp);
     asRegExpObject(thisValue)->setLastIndex(0);
     return JSValue::encode(jsUndefined());
 }
index eb5f8df42e8d34092b8cee243246f98565ca82db..83e75be0252912d4d349cffab61492cd8abf5f5a 100644 (file)
@@ -28,7 +28,7 @@ namespace JSC {
 
     class RegExpPrototype : public RegExpObject {
     public:
-        RegExpPrototype(ExecState*, JSGlobalObject*, Structure*);
+        RegExpPrototype(ExecState*, JSGlobalObject*, Structure*, RegExp*);
 
         static const ClassInfo s_info;
 
index d2129e25f1dc6a106c5d53f755386da151334924..e70b38836ca31368fee486f79f1fd52fc8b95263 100644 (file)
@@ -606,7 +606,7 @@ EncodedJSValue JSC_HOST_CALL stringProtoFuncMatch(ExecState* exec)
 
     JSValue a0 = exec->argument(0);
 
-    RefPtr<RegExp> reg;
+    RegExp* reg;
     if (a0.inherits(&RegExpObject::s_info))
         reg = asRegExpObject(a0)->regExp();
     else {
@@ -620,7 +620,7 @@ EncodedJSValue JSC_HOST_CALL stringProtoFuncMatch(ExecState* exec)
     RegExpConstructor* regExpConstructor = exec->lexicalGlobalObject()->regExpConstructor();
     int pos;
     int matchLength = 0;
-    regExpConstructor->performMatch(*globalData, reg.get(), s, 0, pos, matchLength);
+    regExpConstructor->performMatch(*globalData, reg, s, 0, pos, matchLength);
     if (!(reg->global())) {
         // case without 'g' flag is handled like RegExp.prototype.exec
         if (pos < 0)
@@ -633,7 +633,7 @@ EncodedJSValue JSC_HOST_CALL stringProtoFuncMatch(ExecState* exec)
     while (pos >= 0) {
         list.append(jsSubstring(exec, s, pos, matchLength));
         pos += matchLength == 0 ? 1 : matchLength;
-        regExpConstructor->performMatch(*globalData, reg.get(), s, pos, pos, matchLength);
+        regExpConstructor->performMatch(*globalData, reg, s, pos, pos, matchLength);
     }
     if (list.isEmpty()) {
         // if there are no matches at all, it's important to return
@@ -655,7 +655,7 @@ EncodedJSValue JSC_HOST_CALL stringProtoFuncSearch(ExecState* exec)
 
     JSValue a0 = exec->argument(0);
 
-    RefPtr<RegExp> reg;
+    RegExp* reg;
     if (a0.inherits(&RegExpObject::s_info))
         reg = asRegExpObject(a0)->regExp();
     else { 
@@ -669,7 +669,7 @@ EncodedJSValue JSC_HOST_CALL stringProtoFuncSearch(ExecState* exec)
     RegExpConstructor* regExpConstructor = exec->lexicalGlobalObject()->regExpConstructor();
     int pos;
     int matchLength = 0;
-    regExpConstructor->performMatch(*globalData, reg.get(), s, 0, pos, matchLength);
+    regExpConstructor->performMatch(*globalData, reg, s, 0, pos, matchLength);
     return JSValue::encode(jsNumber(pos));
 }
 
index 9542a1a75a33e811958ef87ba7f74a9950200e34..f007e3a3ad4e9e3c7098963ea87d807e8f2cbbbc 100644 (file)
@@ -1,12 +1,3 @@
-2011-05-25  Oliver Hunt  <oliver@apple.com>
-
-        Revert last change, something weird happened when I went to land.
-
-        * bindings/js/SerializedScriptValue.cpp:
-        (WebCore::CloneDeserializer::readTerminal):
-        * bridge/qt/qt_runtime.cpp:
-        (JSC::Bindings::convertQVariantToValue):
-
 2011-05-25  James Robinson  <jamesr@chromium.org>
 
         Reviewed by Geoffrey Garen
index bbe0ca44249e62a793204fc505c7577c14b61fc1..74bcbba9e8d4aa8f8a18bd754371957e34e8d1a0 100644 (file)
@@ -1166,7 +1166,7 @@ private:
                 return JSValue();
             RegExpFlags reFlags = regExpFlags(flags->ustring());
             ASSERT(reFlags != InvalidFlags);
-            RefPtr<RegExp> regExp = RegExp::create(&m_exec->globalData(), pattern->ustring(), reFlags);
+            RegExp* regExp = RegExp::create(&m_exec->globalData(), pattern->ustring(), reFlags);
             return new (m_exec) RegExpObject(m_exec->lexicalGlobalObject(), m_globalObject->regExpStructure(), regExp); 
         }
         case ObjectReferenceTag: {
index a17eb3186283fd55b9cc3110f0f51102c1f0a4dd..1c1df74b6cc6cc463e983221f9e7ba45c9f7f132 100644 (file)
@@ -861,9 +861,9 @@ JSValue convertQVariantToValue(ExecState* exec, PassRefPtr<RootObject> root, con
             UString pattern((UChar*)re.pattern().utf16(), re.pattern().length());
             RegExpFlags flags = (re.caseSensitivity() == Qt::CaseInsensitive) ? FlagIgnoreCase : NoFlags;
 
-            RefPtr<JSC::RegExp> regExp = JSC::RegExp::create(&exec->globalData(), pattern, flags);
+            JSC::RegExp* regExp = JSC::RegExp::create(&exec->globalData(), pattern, flags);
             if (regExp->isValid())
-                return new (exec) RegExpObject(exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->regExpStructure(), regExp.release());
+                return new (exec) RegExpObject(exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->regExpStructure(), regExp);
             return jsNull();
         }
     }