JSCell.h 7.5 KB
Newer Older
weinig@apple.com's avatar
weinig@apple.com committed
1 2 3
/*
 *  Copyright (C) 1999-2001 Harri Porten (porten@kde.org)
 *  Copyright (C) 2001 Peter Kelly (pmk@post.com)
4
 *  Copyright (C) 2003, 2004, 2005, 2007, 2008, 2009 Apple Inc. All rights reserved.
weinig@apple.com's avatar
weinig@apple.com committed
5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Library General Public
 *  License as published by the Free Software Foundation; either
 *  version 2 of the License, or (at your option) any later version.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Library General Public License for more details.
 *
 *  You should have received a copy of the GNU Library General Public License
 *  along with this library; see the file COPYING.LIB.  If not, write to
 *  the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
 *  Boston, MA 02110-1301, USA.
 *
 */

#ifndef JSCell_h
#define JSCell_h

26 27
#include "CallData.h"
#include "ConstructData.h"
28
#include "Heap.h"
29
#include "JSLock.h"
30
#include "SlotVisitor.h"
31
#include "TypedArrayType.h"
32
#include "WriteBarrier.h"
33
#include <wtf/Noncopyable.h>
weinig@apple.com's avatar
weinig@apple.com committed
34

35
namespace JSC {
weinig@apple.com's avatar
weinig@apple.com committed
36

37
class CopyVisitor;
38
class ExecState;
39
class JSArrayBufferView;
40 41 42 43 44 45 46 47 48 49 50 51
class JSDestructibleObject;
class JSGlobalObject;
class LLIntOffsetsExtractor;
class PropertyDescriptor;
class PropertyNameArray;
class Structure;

enum EnumerationMode {
    ExcludeDontEnumProperties,
    IncludeDontEnumProperties
};

oliver@apple.com's avatar
oliver@apple.com committed
52 53 54
template<typename T> void* allocateCell(Heap&);
template<typename T> void* allocateCell(Heap&, size_t);

55 56 57 58 59 60 61 62 63 64 65 66
#define DECLARE_EXPORT_INFO                                             \
    protected:                                                          \
        static JS_EXPORTDATA const ::JSC::ClassInfo s_info;             \
    public:                                                             \
        static const ::JSC::ClassInfo* info() { return &s_info; }

#define DECLARE_INFO                                                    \
    protected:                                                          \
        static const ::JSC::ClassInfo s_info;                           \
    public:                                                             \
        static const ::JSC::ClassInfo* info() { return &s_info; }

67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82
class JSCell {
    friend class JSValue;
    friend class MarkedBlock;
    template<typename T> friend void* allocateCell(Heap&);
    template<typename T> friend void* allocateCell(Heap&, size_t);

public:
    static const unsigned StructureFlags = 0;

    static const bool needsDestruction = false;
    static const bool hasImmortalStructure = false;

    enum CreatingEarlyCellTag { CreatingEarlyCell };
    JSCell(CreatingEarlyCellTag);

protected:
83
    JSCell(VM&, Structure*);
84 85 86 87 88 89 90 91 92 93 94 95
    JS_EXPORT_PRIVATE static void destroy(JSCell*);

public:
    // Querying the type.
    bool isString() const;
    bool isObject() const;
    bool isGetterSetter() const;
    bool isProxy() const;
    bool inherits(const ClassInfo*) const;
    bool isAPIValueWrapper() const;

    Structure* structure() const;
96
    void setStructure(VM&, Structure*);
97 98 99 100 101 102 103 104 105
    void clearStructure() { m_structure.clear(); }

    const char* className();

    // Extracting the value.
    JS_EXPORT_PRIVATE bool getString(ExecState*, String&) const;
    JS_EXPORT_PRIVATE String getString(ExecState*) const; // null string if not a string
    JS_EXPORT_PRIVATE JSObject* getObject(); // NULL if not an object
    const JSObject* getObject() const; // NULL if not an object
106
        
107 108 109 110 111 112 113
    JS_EXPORT_PRIVATE static CallType getCallData(JSCell*, CallData&);
    JS_EXPORT_PRIVATE static ConstructType getConstructData(JSCell*, ConstructData&);

    // Basic conversions.
    JS_EXPORT_PRIVATE JSValue toPrimitive(ExecState*, PreferredPrimitiveType) const;
    bool getPrimitiveNumber(ExecState*, double& number, JSValue&) const;
    bool toBoolean(ExecState*) const;
114
    TriState pureToBoolean() const;
115 116 117 118
    JS_EXPORT_PRIVATE double toNumber(ExecState*) const;
    JS_EXPORT_PRIVATE JSObject* toObject(ExecState*, JSGlobalObject*) const;

    static void visitChildren(JSCell*, SlotVisitor&);
119
    JS_EXPORT_PRIVATE static void copyBackingStore(JSCell*, CopyVisitor&, CopyToken);
120 121 122 123

    // Object operations, with the toObject operation included.
    const ClassInfo* classInfo() const;
    const MethodTable* methodTable() const;
124
    const MethodTable* methodTableForDestruction() const;
125 126
    static void put(JSCell*, ExecState*, PropertyName, JSValue, PutPropertySlot&);
    static void putByIndex(JSCell*, ExecState*, unsigned propertyName, JSValue, bool shouldThrow);
127
        
128 129
    static bool deleteProperty(JSCell*, ExecState*, PropertyName);
    static bool deletePropertyByIndex(JSCell*, ExecState*, unsigned propertyName);
130

131
    static JSValue toThis(JSCell*, ExecState*, ECMAMode);
132

133 134
    void zap() { *reinterpret_cast<uintptr_t**>(this) = 0; }
    bool isZapped() const { return !*reinterpret_cast<uintptr_t* const*>(this); }
darin@apple.com's avatar
darin@apple.com committed
135

mhahnenberg@apple.com's avatar
mhahnenberg@apple.com committed
136
    JSValue fastGetOwnProperty(ExecState*, const String&);
137

138
    static ptrdiff_t structureOffset()
139
    {
140
        return OBJECT_OFFSETOF(JSCell, m_structure);
141 142
    }

143
    void* structureAddress()
144
    {
145
        return &m_structure;
146
    }
147 148
        
#if ENABLE(GC_VALIDATION)
149
    Structure* unvalidatedStructure() const { return m_structure.unvalidatedGet(); }
150 151
#endif
        
152
    static const TypedArrayType TypedArrayStorageType = NotTypedArray;
153 154
protected:

155 156
    void finishCreation(VM&);
    void finishCreation(VM&, Structure*, CreatingEarlyCellTag);
157 158 159

    // Dummy implementations of override-able static functions for classes to put in their MethodTable
    static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
160 161 162
    static NO_RETURN_DUE_TO_CRASH void getOwnPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode);
    static NO_RETURN_DUE_TO_CRASH void getOwnNonIndexPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode);
    static NO_RETURN_DUE_TO_CRASH void getPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode);
163 164
    static String className(const JSObject*);
    JS_EXPORT_PRIVATE static bool customHasInstance(JSObject*, ExecState*, JSValue);
165
    static bool defineOwnProperty(JSObject*, ExecState*, PropertyName, const PropertyDescriptor&, bool shouldThrow);
166 167
    static bool getOwnPropertySlot(JSObject*, ExecState*, PropertyName, PropertySlot&);
    static bool getOwnPropertySlotByIndex(JSObject*, ExecState*, unsigned propertyName, PropertySlot&);
168
    JS_EXPORT_PRIVATE static ArrayBuffer* slowDownAndWasteMemory(JSArrayBufferView*);
169
    JS_EXPORT_PRIVATE static PassRefPtr<ArrayBufferView> getTypedArrayImpl(JSArrayBufferView*);
170 171 172 173 174 175

private:
    friend class LLIntOffsetsExtractor;
        
    WriteBarrier<Structure> m_structure;
};
176

177 178 179
template<typename To, typename From>
inline To jsCast(From* from)
{
180
    ASSERT(!from || from->JSCell::inherits(std::remove_pointer<To>::type::info()));
181 182
    return static_cast<To>(from);
}
183
    
184 185 186
template<typename To>
inline To jsCast(JSValue from)
{
187
    ASSERT(from.isCell() && from.asCell()->JSCell::inherits(std::remove_pointer<To>::type::info()));
188 189 190 191 192 193
    return static_cast<To>(from.asCell());
}

template<typename To, typename From>
inline To jsDynamicCast(From* from)
{
194
    return from->inherits(std::remove_pointer<To>::type::info()) ? static_cast<To>(from) : 0;
195 196 197 198 199
}

template<typename To>
inline To jsDynamicCast(JSValue from)
{
200
    return from.isCell() && from.asCell()->inherits(std::remove_pointer<To>::type::info()) ? static_cast<To>(from.asCell()) : 0;
201
}
202

203
} // namespace JSC
weinig@apple.com's avatar
weinig@apple.com committed
204 205

#endif // JSCell_h