+ void copyToArguments(ExecState*, CallFrame*, uint32_t copyLength, int32_t firstArgumentOffset);
+ void tearOff(CallFrame*);
+ void tearOff(CallFrame*, InlineCallFrame*);
+ bool isTornOff() const { return m_registerArray.get(); }
+ void didTearOffActivation(ExecState*, JSActivation*);
+
+ static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
+ {
+ return Structure::create(vm, globalObject, prototype, TypeInfo(ArgumentsType, StructureFlags), info());
+ }
+
+ static ptrdiff_t offsetOfActivation() { return OBJECT_OFFSETOF(Arguments, m_activation); }
+ static ptrdiff_t offsetOfNumArguments() { return OBJECT_OFFSETOF(Arguments, m_numArguments); }
+ static ptrdiff_t offsetOfOverrodeLength() { return OBJECT_OFFSETOF(Arguments, m_overrodeLength); }
+ static ptrdiff_t offsetOfIsStrictMode() { return OBJECT_OFFSETOF(Arguments, m_isStrictMode); }
+ static ptrdiff_t offsetOfRegisters() { return OBJECT_OFFSETOF(Arguments, m_registers); }
+ static ptrdiff_t offsetOfRegisterArray() { return OBJECT_OFFSETOF(Arguments, m_registerArray); }
+ static ptrdiff_t offsetOfSlowArgumentData() { return OBJECT_OFFSETOF(Arguments, m_slowArgumentData); }
+ static ptrdiff_t offsetOfCallee() { return OBJECT_OFFSETOF(Arguments, m_callee); }
+
+ static size_t allocationSize(size_t inlineCapacity)
+ {
+ ASSERT_UNUSED(inlineCapacity, !inlineCapacity);
+ return sizeof(Arguments);
+ }
+
+protected:
+ static const unsigned StructureFlags = OverridesGetOwnPropertySlot | InterceptsGetOwnPropertySlotByIndexEvenWhenLengthIsNotZero | OverridesVisitChildren | OverridesGetPropertyNames | JSObject::StructureFlags;
+
+ void finishCreation(CallFrame*);
+ void finishCreation(CallFrame*, InlineCallFrame*);
+
+private:
+ static bool getOwnPropertySlot(JSObject*, ExecState*, PropertyName, PropertySlot&);
+ static bool getOwnPropertySlotByIndex(JSObject*, ExecState*, unsigned propertyName, PropertySlot&);
+ static void getOwnPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode);
+ static void put(JSCell*, ExecState*, PropertyName, JSValue, PutPropertySlot&);
+ static void putByIndex(JSCell*, ExecState*, unsigned propertyName, JSValue, bool shouldThrow);
+ static bool deleteProperty(JSCell*, ExecState*, PropertyName);
+ static bool deletePropertyByIndex(JSCell*, ExecState*, unsigned propertyName);
+ static bool defineOwnProperty(JSObject*, ExecState*, PropertyName, const PropertyDescriptor&, bool shouldThrow);
+ void createStrictModeCallerIfNecessary(ExecState*);
+ void createStrictModeCalleeIfNecessary(ExecState*);
+
+ size_t registerArraySizeInBytes() const { return sizeof(WriteBarrier<Unknown>) * m_numArguments; }
+ void allocateRegisterArray(VM&);
+ bool isArgument(size_t);
+ bool trySetArgument(VM&, size_t argument, JSValue);
+ JSValue tryGetArgument(size_t argument);
+ bool isDeletedArgument(size_t);
+ bool tryDeleteArgument(VM&, size_t);
+ WriteBarrierBase<Unknown>& argument(size_t);
+ void allocateSlowArguments(VM&);
+
+ void init(CallFrame*);
+
+ WriteBarrier<JSActivation> m_activation;
+
+ unsigned m_numArguments;
+
+ // We make these full byte booleans to make them easy to test from the JIT,
+ // and because even if they were single-bit booleans we still wouldn't save
+ // any space.
+ bool m_overrodeLength;
+ bool m_overrodeCallee;
+ bool m_overrodeCaller;
+ bool m_isStrictMode;
+
+ WriteBarrierBase<Unknown>* m_registers;
+ CopyWriteBarrier<WriteBarrier<Unknown>> m_registerArray;
+
+public:
+ struct SlowArgumentData {
+ public:
+ SlowArgumentData()
+ : m_bytecodeToMachineCaptureOffset(0)