Commit 34e919eb authored by ggaren@apple.com's avatar ggaren@apple.com

Stop #include-ing all of JavaScriptCore in every DOM-related file

https://bugs.webkit.org/show_bug.cgi?id=114220

Reviewed by Sam Weinig.

../JavaScriptCore: 

I separated WeakInlines.h from Weak.h so WebCore data types that need
to declare a Weak<T> data member don't have to #include all of the
infrastructure for accessing that data member.

This also required separating Weak<T> from PassWeak<T> by removing the
WeakImplAccessor class template and pushing code down into its subclasses.

* API/JSWeakObjectMapRefPrivate.cpp:
* JavaScriptCore.xcodeproj/project.pbxproj:
* bytecode/UnlinkedCodeBlock.h:
* heap/PassWeak.h:
(JSC):
(PassWeak):
(JSC::::PassWeak):
(JSC::::operator):
(JSC::::get):
* heap/SlotVisitorInlines.h:
* heap/Weak.h:
(JSC):
(Weak):
* heap/WeakInlines.h: Copied from Source/JavaScriptCore/heap/Weak.h.
(JSC):
(JSC::::Weak):
(JSC::::operator):
(JSC::::get):
(JSC::::was):
(JSC::weakClear):
* jit/JITThunks.h:
* runtime/RegExpCache.h:
* runtime/Structure.h:
* runtime/WeakGCMap.h:

../WebCore: 

I separated ScriptWrappableInlines.h from ScriptWrappable.h so
WebCore data types that inherit from ScriptWrappable don't
have to #include all of the infrastructure for accessing that data member.

* ForwardingHeaders/heap/PassWeak.h: Added.
* ForwardingHeaders/heap/WeakInlines.h: Added.
* WebCore.xcodeproj/project.pbxproj:
* bindings/js/DOMWrapperWorld.h:
* bindings/js/JSDOMBinding.h:
(JSC):
* bindings/js/JSEventListener.h:
* bindings/js/JSMutationCallback.cpp:
* bindings/js/JSNodeFilterCondition.h:
* bindings/js/ScriptWrappable.h:
(JSC):
(WebCore):
(ScriptWrappable):
* bindings/js/ScriptWrappableInlines.h: Added.
(WebCore):
(WebCore::ScriptWrappable::wrapper):
(WebCore::ScriptWrappable::setWrapper):
(WebCore::ScriptWrappable::clearWrapper):
* bridge/qt/qt_instance.h:
* bridge/qt/qt_runtime.h:
* bridge/runtime_root.cpp:
* bridge/runtime_root.h:
* css/StylePropertySet.cpp:
* dom/LiveNodeList.cpp:
(WebCore::LiveNodeListBase::reportMemoryUsage):
* dom/Node.cpp:
(WebCore::Node::reportMemoryUsage):
* inspector/InspectorDebuggerAgent.cpp:
* inspector/NetworkResourcesData.cpp:
* loader/cache/CachedSVGDocument.cpp:
* xml/XMLHttpRequest.cpp:
(WebCore::XMLHttpRequest::reportMemoryUsage):

../WebKit2: 

* Shared/WebCoreArgumentCoders.cpp:
* WebProcess/Plugins/Netscape/NPRuntimeObjectMap.h:


git-svn-id: http://svn.webkit.org/repository/webkit/trunk@147962 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent 33caa456
......@@ -32,6 +32,7 @@
#include "JSCallbackObject.h"
#include "JSWeakObjectMapRefInternal.h"
#include "Operations.h"
#include "Weak.h"
#include <wtf/HashMap.h>
#include <wtf/text/StringHash.h>
......
2013-04-08 Geoffrey Garen <ggaren@apple.com>
Stop #include-ing all of JavaScriptCore in every DOM-related file
https://bugs.webkit.org/show_bug.cgi?id=114220
Reviewed by Sam Weinig.
I separated WeakInlines.h from Weak.h so WebCore data types that need
to declare a Weak<T> data member don't have to #include all of the
infrastructure for accessing that data member.
This also required separating Weak<T> from PassWeak<T> by removing the
WeakImplAccessor class template and pushing code down into its subclasses.
* API/JSWeakObjectMapRefPrivate.cpp:
* JavaScriptCore.xcodeproj/project.pbxproj:
* bytecode/UnlinkedCodeBlock.h:
* heap/PassWeak.h:
(JSC):
(PassWeak):
(JSC::::PassWeak):
(JSC::::operator):
(JSC::::get):
* heap/SlotVisitorInlines.h:
* heap/Weak.h:
(JSC):
(Weak):
* heap/WeakInlines.h: Copied from Source/JavaScriptCore/heap/Weak.h.
(JSC):
(JSC::::Weak):
(JSC::::operator):
(JSC::::get):
(JSC::::was):
(JSC::weakClear):
* jit/JITThunks.h:
* runtime/RegExpCache.h:
* runtime/Structure.h:
* runtime/WeakGCMap.h:
2013-04-05 Roger Fong <roger_fong@apple.com>
Windows build fix fix.
......@@ -491,6 +491,7 @@
14BD59C50A3E8F9F00BAF59C /* JavaScriptCore.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 932F5BD90822A1C700736975 /* JavaScriptCore.framework */; };
14BD5A300A3E91F600BAF59C /* JSContextRef.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 14BD5A290A3E91F600BAF59C /* JSContextRef.cpp */; };
14BD5A320A3E91F600BAF59C /* JSValueRef.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 14BD5A2B0A3E91F600BAF59C /* JSValueRef.cpp */; };
14BE7D3317135CF400D1807A /* WeakInlines.h in Headers */ = {isa = PBXBuildFile; fileRef = 14BE7D3217135CF400D1807A /* WeakInlines.h */; settings = {ATTRIBUTES = (Private, ); }; };
14BFCE6910CDB1FC00364CCE /* WeakGCMap.h in Headers */ = {isa = PBXBuildFile; fileRef = 14BFCE6810CDB1FC00364CCE /* WeakGCMap.h */; settings = {ATTRIBUTES = (Private, ); }; };
14C5242B0F5355E900BA3D04 /* JITStubs.h in Headers */ = {isa = PBXBuildFile; fileRef = 14A6581A0F4E36F4000150FD /* JITStubs.h */; settings = {ATTRIBUTES = (Private, ); }; };
14CA958B16AB50DE00938A06 /* StaticPropertyAnalyzer.h in Headers */ = {isa = PBXBuildFile; fileRef = 14CA958A16AB50DE00938A06 /* StaticPropertyAnalyzer.h */; settings = {ATTRIBUTES = (Private, ); }; };
......@@ -1353,6 +1354,7 @@
14BD5A2A0A3E91F600BAF59C /* JSContextRef.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = JSContextRef.h; sourceTree = "<group>"; };
14BD5A2B0A3E91F600BAF59C /* JSValueRef.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = JSValueRef.cpp; sourceTree = "<group>"; };
14BD5A2D0A3E91F600BAF59C /* testapi.c */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.c; name = testapi.c; path = API/tests/testapi.c; sourceTree = "<group>"; };
14BE7D3217135CF400D1807A /* WeakInlines.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WeakInlines.h; sourceTree = "<group>"; };
14BFCE6810CDB1FC00364CCE /* WeakGCMap.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WeakGCMap.h; sourceTree = "<group>"; };
14CA958A16AB50DE00938A06 /* StaticPropertyAnalyzer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StaticPropertyAnalyzer.h; sourceTree = "<group>"; };
14CA958C16AB50FA00938A06 /* ObjectAllocationProfile.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ObjectAllocationProfile.h; sourceTree = "<group>"; };
......@@ -2113,6 +2115,8 @@
C21122DE15DD9AB300790E3A /* GCThreadSharedData.cpp */,
C21122DF15DD9AB300790E3A /* GCThreadSharedData.h */,
142E312B134FF0A600AFADB5 /* Handle.h */,
C28318FF16FE4B7D00157BFD /* HandleBlock.h */,
C283190116FE533E00157BFD /* HandleBlockInlines.h */,
142E312C134FF0A600AFADB5 /* HandleSet.cpp */,
142E312D134FF0A600AFADB5 /* HandleSet.h */,
142E312E134FF0A600AFADB5 /* HandleStack.cpp */,
......@@ -2146,11 +2150,14 @@
142D6F0F13539A4100B02E86 /* MarkStack.h */,
C21122E015DD9AB300790E3A /* MarkStackInlines.h */,
1497209014EB831500FEB1B7 /* PassWeak.h */,
C20B25981706536200C21F4E /* Region.h */,
C225494215F7DBAA0065E898 /* SlotVisitor.cpp */,
14BA78F013AAB88F005B7C2C /* SlotVisitor.h */,
0FCB408515C0A3C30048932B /* SlotVisitorInlines.h */,
142E3132134FF0A600AFADB5 /* Strong.h */,
145722851437E140005FDE26 /* StrongInlines.h */,
C2DF442D1707AC0100A5CA96 /* SuperRegion.cpp */,
C2DF442E1707AC0100A5CA96 /* SuperRegion.h */,
141448CC13A1783700F5BA1A /* TinyBloomFilter.h */,
0F5F08CE146C762F000472A9 /* UnconditionalFinalizer.h */,
0FC815121405118600CFA603 /* VTableSpectrum.cpp */,
......@@ -2161,17 +2168,13 @@
14F7256314EE265E00B1652B /* WeakHandleOwner.cpp */,
14F7256414EE265E00B1652B /* WeakHandleOwner.h */,
14E84F9D14EE1ACC00D6D5D4 /* WeakImpl.h */,
14BE7D3217135CF400D1807A /* WeakInlines.h */,
0F242DA513F3B1BB007ADD4C /* WeakReferenceHarvester.h */,
14E84F9B14EE1ACC00D6D5D4 /* WeakSet.cpp */,
14E84F9C14EE1ACC00D6D5D4 /* WeakSet.h */,
14150132154BB13F005D8C98 /* WeakSetInlines.h */,
0FC8150814043BCA00CFA603 /* WriteBarrierSupport.cpp */,
0FC8150914043BD200CFA603 /* WriteBarrierSupport.h */,
C28318FF16FE4B7D00157BFD /* HandleBlock.h */,
C283190116FE533E00157BFD /* HandleBlockInlines.h */,
C20B25981706536200C21F4E /* Region.h */,
C2DF442D1707AC0100A5CA96 /* SuperRegion.cpp */,
C2DF442E1707AC0100A5CA96 /* SuperRegion.h */,
);
path = heap;
sourceTree = "<group>";
......@@ -3308,6 +3311,7 @@
0FF729BC166AD360000F5BA3 /* ProfilerCompiledBytecode.h in Headers */,
0FF729BD166AD360000F5BA3 /* ProfilerDatabase.h in Headers */,
0FF729BE166AD360000F5BA3 /* ProfilerExecutionCounter.h in Headers */,
14BE7D3317135CF400D1807A /* WeakInlines.h in Headers */,
0FF729BF166AD360000F5BA3 /* ProfilerOrigin.h in Headers */,
0FF729C0166AD360000F5BA3 /* ProfilerOriginStack.h in Headers */,
0FB1058C1675483300F8AB6E /* ProfilerOSRExit.h in Headers */,
......
......@@ -38,7 +38,6 @@
#include "RegExp.h"
#include "SpecialPointer.h"
#include "SymbolTable.h"
#include "Weak.h"
#include <wtf/RefCountedArray.h>
#include <wtf/Vector.h>
......
/*
* Copyright (C) 2012 Apple Inc. All rights reserved.
* Copyright (C) 2012, 2013 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
......@@ -34,29 +34,14 @@
namespace JSC {
template<typename T> class Weak;
template<typename T> class PassWeak;
template<typename T> PassWeak<T> adoptWeak(WeakImpl*);
template<typename Base, typename T> class WeakImplAccessor {
template<typename T> class PassWeak {
public:
typedef T* GetType;
T* operator->() const;
T& operator*() const;
GetType get() const;
bool was(GetType) const;
};
template<typename T> class PassWeak : public WeakImplAccessor<PassWeak<T>, T> {
public:
friend class WeakImplAccessor<PassWeak<T>, T>;
typedef typename WeakImplAccessor<PassWeak<T>, T>::GetType GetType;
PassWeak();
PassWeak(std::nullptr_t);
PassWeak(GetType, WeakHandleOwner* = 0, void* context = 0);
PassWeak(T*, WeakHandleOwner* = 0, void* context = 0);
// It somewhat breaks the type system to allow transfer of ownership out of
// a const PassWeak. However, it makes it much easier to work with PassWeak
......@@ -66,10 +51,14 @@ public:
~PassWeak();
T* operator->() const;
T& operator*() const;
T* get() const;
bool operator!() const;
// This conversion operator allows implicit conversion to bool but not to other integer types.
typedef JSValue (PassWeak::*UnspecifiedBoolType);
typedef void* (PassWeak::*UnspecifiedBoolType);
operator UnspecifiedBoolType*() const;
WeakImpl* leakImpl() const WARN_UNUSED_RETURN;
......@@ -81,30 +70,6 @@ private:
WeakImpl* m_impl;
};
template<typename Base, typename T> inline T* WeakImplAccessor<Base, T>::operator->() const
{
ASSERT(static_cast<const Base*>(this)->m_impl && static_cast<const Base*>(this)->m_impl->state() == WeakImpl::Live);
return jsCast<T*>(static_cast<const Base*>(this)->m_impl->jsValue().asCell());
}
template<typename Base, typename T> inline T& WeakImplAccessor<Base, T>::operator*() const
{
ASSERT(static_cast<const Base*>(this)->m_impl && static_cast<const Base*>(this)->m_impl->state() == WeakImpl::Live);
return *jsCast<T*>(static_cast<const Base*>(this)->m_impl->jsValue().asCell());
}
template<typename Base, typename T> inline typename WeakImplAccessor<Base, T>::GetType WeakImplAccessor<Base, T>::get() const
{
if (!static_cast<const Base*>(this)->m_impl || static_cast<const Base*>(this)->m_impl->state() != WeakImpl::Live)
return GetType();
return jsCast<T*>(static_cast<const Base*>(this)->m_impl->jsValue().asCell());
}
template<typename Base, typename T> inline bool WeakImplAccessor<Base, T>::was(typename WeakImplAccessor<Base, T>::GetType other) const
{
return jsCast<T*>(static_cast<const Base*>(this)->m_impl->jsValue().asCell()) == other;
}
template<typename T> inline PassWeak<T>::PassWeak()
: m_impl(0)
{
......@@ -115,8 +80,8 @@ template<typename T> inline PassWeak<T>::PassWeak(std::nullptr_t)
{
}
template<typename T> inline PassWeak<T>::PassWeak(typename PassWeak<T>::GetType getType, WeakHandleOwner* weakOwner, void* context)
: m_impl(getType ? WeakSet::allocate(getType, weakOwner, context) : 0)
template<typename T> inline PassWeak<T>::PassWeak(T* cell, WeakHandleOwner* weakOwner, void* context)
: m_impl(cell ? WeakSet::allocate(cell, weakOwner, context) : 0)
{
}
......@@ -137,6 +102,25 @@ template<typename T> inline PassWeak<T>::~PassWeak()
WeakSet::deallocate(m_impl);
}
template<typename T> inline T* PassWeak<T>::operator->() const
{
ASSERT(m_impl && m_impl->state() == WeakImpl::Live);
return jsCast<T*>(m_impl->jsValue().asCell());
}
template<typename T> inline T& PassWeak<T>::operator*() const
{
ASSERT(m_impl && m_impl->state() == WeakImpl::Live);
return *jsCast<T*>(m_impl->jsValue().asCell());
}
template<typename T> inline T* PassWeak<T>::get() const
{
if (!m_impl || m_impl->state() != WeakImpl::Live)
return 0;
return jsCast<T*>(m_impl->jsValue().asCell());
}
template<typename T> inline bool PassWeak<T>::operator!() const
{
return !m_impl || m_impl->state() != WeakImpl::Live || !m_impl->jsValue();
......
......@@ -31,6 +31,7 @@
#include "Options.h"
#include "SlotVisitor.h"
#include "Weak.h"
#include "WeakInlines.h"
namespace JSC {
......
/*
* Copyright (C) 2009, 2012 Apple Inc. All rights reserved.
* Copyright (C) 2009, 2012, 2013 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
......@@ -26,22 +26,21 @@
#ifndef Weak_h
#define Weak_h
#include "PassWeak.h"
#include "WeakSetInlines.h"
#include <wtf/Assertions.h>
#include <wtf/HashMap.h>
#include <wtf/Noncopyable.h>
#include <wtf/NullPtr.h>
namespace JSC {
template<typename T> class Weak : public WeakImplAccessor<Weak<T>, T> {
template<typename T> class PassWeak;
class WeakImpl;
class WeakHandleOwner;
template<typename T> class Weak {
WTF_MAKE_NONCOPYABLE(Weak);
public:
friend class WeakImplAccessor<Weak<T>, T>;
typedef typename WeakImplAccessor<Weak<T>, T>::GetType GetType;
Weak();
explicit Weak(std::nullptr_t);
explicit Weak(GetType, WeakHandleOwner* = 0, void* context = 0);
explicit Weak(T*, WeakHandleOwner* = 0, void* context = 0);
enum HashTableDeletedValueTag { HashTableDeletedValue };
bool isHashTableDeletedValue() const;
......@@ -55,9 +54,14 @@ public:
Weak& operator=(const PassWeak<T>&);
bool operator!() const;
T* operator->() const;
T& operator*() const;
T* get() const;
bool was(T*) const;
// This conversion operator allows implicit conversion to bool but not to other integer types.
typedef JSValue (HandleBase::*UnspecifiedBoolType);
typedef void* (Weak::*UnspecifiedBoolType);
operator UnspecifiedBoolType*() const;
PassWeak<T> release();
......@@ -69,145 +73,6 @@ private:
WeakImpl* m_impl;
};
template<typename T> inline Weak<T>::Weak()
: m_impl(0)
{
}
template<typename T> inline Weak<T>::Weak(std::nullptr_t)
: m_impl(0)
{
}
template<typename T> inline Weak<T>::Weak(typename Weak<T>::GetType getType, WeakHandleOwner* weakOwner, void* context)
: m_impl(getType ? WeakSet::allocate(getType, weakOwner, context) : 0)
{
}
template<typename T> inline bool Weak<T>::isHashTableDeletedValue() const
{
return m_impl == hashTableDeletedValue();
}
template<typename T> inline Weak<T>::Weak(typename Weak<T>::HashTableDeletedValueTag)
: m_impl(hashTableDeletedValue())
{
}
template<typename T> template<typename U> inline Weak<T>::Weak(const PassWeak<U>& other)
: m_impl(other.leakImpl())
{
}
template<typename T> inline Weak<T>::~Weak()
{
clear();
}
template<class T> inline void swap(Weak<T>& a, Weak<T>& b)
{
a.swap(b);
}
template<typename T> inline void Weak<T>::swap(Weak& other)
{
std::swap(m_impl, other.m_impl);
}
template<typename T> inline Weak<T>& Weak<T>::operator=(const PassWeak<T>& o)
{
clear();
m_impl = o.leakImpl();
return *this;
}
template<typename T> inline bool Weak<T>::operator!() const
{
return !m_impl || !m_impl->jsValue() || m_impl->state() != WeakImpl::Live;
}
template<typename T> inline Weak<T>::operator UnspecifiedBoolType*() const
{
return reinterpret_cast<UnspecifiedBoolType*>(!!*this);
}
template<typename T> inline PassWeak<T> Weak<T>::release()
{
PassWeak<T> tmp = adoptWeak<T>(m_impl);
m_impl = 0;
return tmp;
}
template<typename T> inline void Weak<T>::clear()
{
if (!m_impl)
return;
WeakSet::deallocate(m_impl);
m_impl = 0;
}
template<typename T> inline WeakImpl* Weak<T>::hashTableDeletedValue()
{
return reinterpret_cast<WeakImpl*>(-1);
}
template <typename T> inline bool operator==(const Weak<T>& lhs, const Weak<T>& rhs)
{
return lhs.get() == rhs.get();
}
// This function helps avoid modifying a weak table while holding an iterator into it. (Object allocation
// can run a finalizer that modifies the table. We avoid that by requiring a pre-constructed object as our value.)
template<typename Map, typename Key, typename Value> inline void weakAdd(Map& map, const Key& key, Value value)
{
ASSERT(!map.get(key));
map.set(key, value); // The table may still have a zombie for value.
}
template<typename Map, typename Key, typename Value> inline void weakRemove(Map& map, const Key& key, Value value)
{
typename Map::iterator it = map.find(key);
ASSERT_UNUSED(value, value);
ASSERT(it != map.end());
ASSERT(it->value.was(value));
ASSERT(!it->value);
map.remove(it);
}
template<typename T> inline void weakClear(Weak<T>& weak, typename Weak<T>::GetType value)
{
ASSERT_UNUSED(value, value);
ASSERT(weak.was(value));
ASSERT(!weak);
weak.clear();
}
} // namespace JSC
namespace WTF {
template<typename T> struct VectorTraits<JSC::Weak<T> > : SimpleClassVectorTraits {
static const bool canCompareWithMemcmp = false;
};
template<typename T> struct HashTraits<JSC::Weak<T> > : SimpleClassHashTraits<JSC::Weak<T> > {
typedef JSC::Weak<T> StorageType;
typedef std::nullptr_t EmptyValueType;
static EmptyValueType emptyValue() { return nullptr; }
typedef JSC::PassWeak<T> PassInType;
static void store(PassInType value, StorageType& storage) { storage = value; }
typedef JSC::PassWeak<T> PassOutType;
static PassOutType passOut(StorageType& value) { return value.release(); }
static PassOutType passOut(EmptyValueType) { return PassOutType(); }
typedef typename StorageType::GetType PeekType;
static PeekType peek(const StorageType& value) { return value.get(); }
static PeekType peek(EmptyValueType) { return PeekType(); }
};
}
#endif // Weak_h
/*
* Copyright (C) 2009, 2012, 2013 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
* THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef WeakInlines_h
#define WeakInlines_h
#include "PassWeak.h"
#include "WeakSetInlines.h"
#include <wtf/Assertions.h>
#include <wtf/HashTraits.h>
namespace JSC {
template<typename T> inline Weak<T>::Weak()
: m_impl(0)
{
}
template<typename T> inline Weak<T>::Weak(std::nullptr_t)
: m_impl(0)
{
}
template<typename T> inline Weak<T>::Weak(T* cell, WeakHandleOwner* weakOwner, void* context)
: m_impl(cell ? WeakSet::allocate(cell, weakOwner, context) : 0)
{
}
template<typename T> inline bool Weak<T>::isHashTableDeletedValue() const
{
return m_impl == hashTableDeletedValue();
}
template<typename T> inline Weak<T>::Weak(typename Weak<T>::HashTableDeletedValueTag)
: m_impl(hashTableDeletedValue())
{
}
template<typename T> template<typename U> inline Weak<T>::Weak(const PassWeak<U>& other)
: m_impl(other.leakImpl())
{
}
template<typename T> inline Weak<T>::~Weak()
{
clear();
}
template<class T> inline void swap(Weak<T>& a, Weak<T>& b)
{
a.swap(b);
}
template<typename T> inline void Weak<T>::swap(Weak& other)
{
std::swap(m_impl, other.m_impl);
}
template<typename T> inline Weak<T>& Weak<T>::operator=(const PassWeak<T>& o)
{
clear();
m_impl = o.leakImpl();
return *this;
}
template<typename T> inline T* Weak<T>::operator->() const
{
ASSERT(m_impl && m_impl->state() == WeakImpl::Live);
return jsCast<T*>(m_impl->jsValue().asCell());
}
template<typename T> inline T& Weak<T>::operator*() const
{
ASSERT(m_impl && m_impl->state() == WeakImpl::Live);
return *jsCast<T*>(m_impl->jsValue().asCell());
}
template<typename T> inline T* Weak<T>::get() const
{
if (!m_impl || m_impl->state() != WeakImpl::Live)
return 0;
return jsCast<T*>(m_impl->jsValue().asCell());
}
template<typename T> inline bool Weak<T>::was(T* other) const
{
return jsCast<T*>(m_impl->jsValue().asCell()) == other;
}
template<typename T> inline bool Weak<T>::operator!() const
{
return !m_impl || !m_impl->jsValue() || m_impl->state() != WeakImpl::Live;
}
template<typename T> inline Weak<T>::operator UnspecifiedBoolType*() const
{
return reinterpret_cast<UnspecifiedBoolType*>(!!*this);
}
template<typename T> inline PassWeak<T> Weak<T>::release()
{
PassWeak<T> tmp = adoptWeak<T>(m_impl);
m_impl = 0;
return tmp;
}
template<typename T> inline void Weak<T>::clear()
{
if (!m_impl)
return;
WeakSet::deallocate(m_impl);
m_impl = 0;
}
template<typename T> inline WeakImpl* Weak<T>::hashTableDeletedValue()
{
return reinterpret_cast<WeakImpl*>(-1);
}
template <typename T> inline bool operator==(const Weak<T>& lhs, const Weak<T>& rhs)
{
return lhs.get() == rhs.get();
}
// This function helps avoid modifying a weak table while holding an iterator into it. (Object allocation
// can run a finalizer that modifies the table. We avoid that by requiring a pre-constructed object as our value.)
template<typename Map, typename Key, typename Value> inline void weakAdd(Map& map, const Key& key, Value value)
{
ASSERT(!map.get(key));
map.set(key, value); // The table may still have a zombie for value.
}
template<typename Map, typename Key, typename Value> inline void weakRemove(Map& map, const Key& key, Value value)
{
typename Map::iterator it = map.find(key);
ASSERT_UNUSED(value, value);
ASSERT(it != map.end());
ASSERT(it->value.was(value));
ASSERT(!it->value);
map.remove(it);
}
template<typename T> inline void weakClear(Weak<T>& weak, T* cell)
{
ASSERT_UNUSED(cell, cell);
ASSERT(weak.was(cell));
ASSERT(!weak);
weak.clear();
}
} // namespace JSC
namespace WTF {
template<typename T> struct VectorTraits<JSC::Weak<T> > : SimpleClassVectorTraits {
static const bool canCompareWithMemcmp = false;
};
template<typename T> struct HashTraits<JSC::Weak<T> > : SimpleClassHashTraits<JSC::Weak<T> > {
typedef JSC::Weak<T> StorageType;