Changeset 243364 in webkit
- Timestamp:
- Mar 21, 2019, 11:45:20 PM (7 years ago)
- Location:
- trunk/Source/JavaScriptCore
- Files:
-
- 6 edited
-
ChangeLog (modified) (1 diff)
-
dfg/DFGSpeculativeJIT.cpp (modified) (2 diffs)
-
ftl/FTLAbstractHeapRepository.h (modified) (1 diff)
-
ftl/FTLLowerDFGToB3.cpp (modified) (2 diffs)
-
runtime/RegExpObject.cpp (modified) (5 diffs)
-
runtime/RegExpObject.h (modified) (8 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/JavaScriptCore/ChangeLog
r243363 r243364 1 2019-03-21 Yusuke Suzuki <ysuzuki@apple.com> 2 3 [JSC] Shrink sizeof(RegExpObject) 4 https://bugs.webkit.org/show_bug.cgi?id=196130 5 6 Reviewed by Saam Barati. 7 8 sizeof(RegExpObject) is 48B due to one bool flag. We should compress this flag into lower bit of RegExp* field so that we can make RegExpObject 32B. 9 It saves memory footprint 1.3% in RAMification's regexp. 10 11 * dfg/DFGSpeculativeJIT.cpp: 12 (JSC::DFG::SpeculativeJIT::compileNewRegexp): 13 (JSC::DFG::SpeculativeJIT::compileSetRegExpObjectLastIndex): 14 * ftl/FTLAbstractHeapRepository.h: 15 * ftl/FTLLowerDFGToB3.cpp: 16 (JSC::FTL::DFG::LowerDFGToB3::compileNewRegexp): 17 (JSC::FTL::DFG::LowerDFGToB3::compileSetRegExpObjectLastIndex): 18 * runtime/RegExpObject.cpp: 19 (JSC::RegExpObject::RegExpObject): 20 (JSC::RegExpObject::visitChildren): 21 (JSC::RegExpObject::getOwnPropertySlot): 22 (JSC::RegExpObject::defineOwnProperty): 23 * runtime/RegExpObject.h: 24 1 25 2019-03-21 Tomas Popela <tpopela@redhat.com> 2 26 -
trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp
r243280 r243364 9791 9791 m_jit.storePtr( 9792 9792 TrustedImmPtr(node->cellOperand()), 9793 CCallHelpers::Address(resultGPR, RegExpObject::offsetOfRegExp ()));9793 CCallHelpers::Address(resultGPR, RegExpObject::offsetOfRegExpAndLastIndexIsNotWritableFlag())); 9794 9794 m_jit.storeValue(lastIndexRegs, CCallHelpers::Address(resultGPR, RegExpObject::offsetOfLastIndex())); 9795 m_jit.store8(TrustedImm32(true), CCallHelpers::Address(resultGPR, RegExpObject::offsetOfLastIndexIsWritable()));9796 9795 m_jit.mutatorFence(*m_jit.vm()); 9797 9796 … … 11131 11130 speculationCheck( 11132 11131 ExoticObjectMode, JSValueRegs(), nullptr, 11133 m_jit.branchTest8( 11134 JITCompiler::Zero, 11135 JITCompiler::Address(regExpGPR, RegExpObject::offsetOfLastIndexIsWritable()))); 11132 m_jit.branchTestPtr( 11133 JITCompiler::NonZero, 11134 JITCompiler::Address(regExpGPR, RegExpObject::offsetOfRegExpAndLastIndexIsNotWritableFlag()), 11135 JITCompiler::TrustedImm32(RegExpObject::lastIndexIsNotWritableFlag))); 11136 11136 } 11137 11137 -
trunk/Source/JavaScriptCore/ftl/FTLAbstractHeapRepository.h
r242397 r243364 97 97 macro(JSSymbolTableObject_symbolTable, JSSymbolTableObject::offsetOfSymbolTable()) \ 98 98 macro(JSWrapperObject_internalValue, JSWrapperObject::internalValueOffset()) \ 99 macro(RegExpObject_regExp , RegExpObject::offsetOfRegExp()) \99 macro(RegExpObject_regExpAndLastIndexIsNotWritableFlag, RegExpObject::offsetOfRegExpAndLastIndexIsNotWritableFlag()) \ 100 100 macro(RegExpObject_lastIndex, RegExpObject::offsetOfLastIndex()) \ 101 macro(RegExpObject_lastIndexIsWritable, RegExpObject::offsetOfLastIndexIsWritable()) \102 101 macro(ShadowChicken_Packet_callee, OBJECT_OFFSETOF(ShadowChicken::Packet, callee)) \ 103 102 macro(ShadowChicken_Packet_frame, OBJECT_OFFSETOF(ShadowChicken::Packet, frame)) \ -
trunk/Source/JavaScriptCore/ftl/FTLLowerDFGToB3.cpp
r243280 r243364 11291 11291 auto structure = m_graph.registerStructure(m_graph.globalObjectFor(m_node->origin.semantic)->regExpStructure()); 11292 11292 LValue fastResultValue = allocateObject<RegExpObject>(structure, m_out.intPtrZero, slowCase); 11293 m_out.storePtr(frozenPointer(regexp), fastResultValue, m_heaps.RegExpObject_regExp );11293 m_out.storePtr(frozenPointer(regexp), fastResultValue, m_heaps.RegExpObject_regExpAndLastIndexIsNotWritableFlag); 11294 11294 m_out.store64(lastIndex, fastResultValue, m_heaps.RegExpObject_lastIndex); 11295 m_out.store32As8(m_out.constInt32(true), m_out.address(fastResultValue, m_heaps.RegExpObject_lastIndexIsWritable));11296 11295 mutatorFence(); 11297 11296 ValueFromBlock fastResult = m_out.anchor(fastResultValue); … … 11379 11378 speculate( 11380 11379 ExoticObjectMode, noValue(), nullptr, 11381 m_out.isZero32(m_out.load8ZeroExt32(regExp, m_heaps.RegExpObject_lastIndexIsWritable))); 11380 m_out.testNonZeroPtr( 11381 m_out.loadPtr(regExp, m_heaps.RegExpObject_regExpAndLastIndexIsNotWritableFlag), 11382 m_out.constIntPtr(RegExpObject::lastIndexIsNotWritableFlag))); 11382 11383 11383 11384 m_out.store64(value, regExp, m_heaps.RegExpObject_lastIndex); -
trunk/Source/JavaScriptCore/runtime/RegExpObject.cpp
r240593 r243364 39 39 RegExpObject::RegExpObject(VM& vm, Structure* structure, RegExp* regExp) 40 40 : JSNonFinalObject(vm, structure) 41 , m_regExp(vm, this, regExp) 42 , m_lastIndexIsWritable(true) 41 , m_regExpAndLastIndexIsNotWritableFlag(bitwise_cast<uintptr_t>(regExp)) // lastIndexIsNotWritableFlag is not set. 43 42 { 44 43 m_lastIndex.setWithoutWriteBarrier(jsNumber(0)); … … 57 56 ASSERT_GC_OBJECT_INHERITS(thisObject, info()); 58 57 Base::visitChildren(thisObject, visitor); 59 visitor.append (thisObject->m_regExp);58 visitor.appendUnbarriered(thisObject->regExp()); 60 59 visitor.append(thisObject->m_lastIndex); 61 60 } … … 66 65 if (propertyName == vm.propertyNames->lastIndex) { 67 66 RegExpObject* regExp = jsCast<RegExpObject*>(object); 68 unsigned attributes = regExp-> m_lastIndexIsWritable? PropertyAttribute::DontDelete | PropertyAttribute::DontEnum : PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly;67 unsigned attributes = regExp->lastIndexIsWritable() ? PropertyAttribute::DontDelete | PropertyAttribute::DontEnum : PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly; 69 68 slot.setValue(regExp, attributes, regExp->getLastIndex()); 70 69 return true; … … 118 117 if (descriptor.isAccessorDescriptor()) 119 118 return typeError(exec, scope, shouldThrow, UnconfigurablePropertyChangeAccessMechanismError); 120 if (!regExp-> m_lastIndexIsWritable) {119 if (!regExp->lastIndexIsWritable()) { 121 120 if (descriptor.writablePresent() && descriptor.writable()) 122 121 return typeError(exec, scope, shouldThrow, UnconfigurablePropertyChangeWritabilityError); … … 130 129 } 131 130 if (descriptor.writablePresent() && !descriptor.writable()) 132 regExp-> m_lastIndexIsWritable = false;131 regExp->setLastIndexIsNotWritable(); 133 132 return true; 134 133 } -
trunk/Source/JavaScriptCore/runtime/RegExpObject.h
r233122 r243364 33 33 static const unsigned StructureFlags = Base::StructureFlags | OverridesGetOwnPropertySlot | OverridesGetPropertyNames; 34 34 35 static constexpr uintptr_t lastIndexIsNotWritableFlag = 1; 36 35 37 static RegExpObject* create(VM& vm, Structure* structure, RegExp* regExp) 36 38 { … … 47 49 } 48 50 49 void setRegExp(VM& vm, RegExp* r) { m_regExp.set(vm, this, r); } 50 RegExp* regExp() const { return m_regExp.get(); } 51 void setRegExp(VM& vm, RegExp* regExp) 52 { 53 uintptr_t result = (m_regExpAndLastIndexIsNotWritableFlag & lastIndexIsNotWritableFlag) | bitwise_cast<uintptr_t>(regExp); 54 m_regExpAndLastIndexIsNotWritableFlag = result; 55 vm.heap.writeBarrier(this, regExp); 56 } 57 58 RegExp* regExp() const 59 { 60 return bitwise_cast<RegExp*>(m_regExpAndLastIndexIsNotWritableFlag & (~lastIndexIsNotWritableFlag)); 61 } 51 62 52 63 bool setLastIndex(ExecState* exec, size_t lastIndex) … … 55 66 auto scope = DECLARE_THROW_SCOPE(vm); 56 67 57 if (LIKELY( m_lastIndexIsWritable)) {68 if (LIKELY(lastIndexIsWritable())) { 58 69 m_lastIndex.setWithoutWriteBarrier(jsNumber(lastIndex)); 59 70 return true; … … 67 78 auto scope = DECLARE_THROW_SCOPE(vm); 68 79 69 if (LIKELY( m_lastIndexIsWritable)) {80 if (LIKELY(lastIndexIsWritable())) { 70 81 m_lastIndex.set(vm, this, lastIndex); 71 82 return true; 72 83 } 73 74 84 return typeError(exec, scope, shouldThrow, ReadonlyPropertyWriteError); 75 85 } … … 96 106 } 97 107 98 static ptrdiff_t offsetOfRegExp ()108 static ptrdiff_t offsetOfRegExpAndLastIndexIsNotWritableFlag() 99 109 { 100 return OBJECT_OFFSETOF(RegExpObject, m_regExp );110 return OBJECT_OFFSETOF(RegExpObject, m_regExpAndLastIndexIsNotWritableFlag); 101 111 } 102 112 … … 104 114 { 105 115 return OBJECT_OFFSETOF(RegExpObject, m_lastIndex); 106 }107 108 static ptrdiff_t offsetOfLastIndexIsWritable()109 {110 return OBJECT_OFFSETOF(RegExpObject, m_lastIndexIsWritable);111 116 } 112 117 … … 123 128 static void visitChildren(JSCell*, SlotVisitor&); 124 129 130 bool lastIndexIsWritable() const 131 { 132 return !(m_regExpAndLastIndexIsNotWritableFlag & lastIndexIsNotWritableFlag); 133 } 134 135 void setLastIndexIsNotWritable() 136 { 137 m_regExpAndLastIndexIsNotWritableFlag = (m_regExpAndLastIndexIsNotWritableFlag | lastIndexIsNotWritableFlag); 138 } 139 125 140 JS_EXPORT_PRIVATE static bool deleteProperty(JSCell*, ExecState*, PropertyName); 126 141 JS_EXPORT_PRIVATE static void getOwnNonIndexPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode); … … 132 147 MatchResult matchInline(ExecState*, JSGlobalObject*, JSString*); 133 148 134 WriteBarrier<RegExp> m_regExp;149 uintptr_t m_regExpAndLastIndexIsNotWritableFlag { 0 }; 135 150 WriteBarrier<Unknown> m_lastIndex; 136 uint8_t m_lastIndexIsWritable;137 151 }; 138 152
Note:
See TracChangeset
for help on using the changeset viewer.