10bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch/* 20bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * Copyright (C) 2009 Google Inc. All rights reserved. 30bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * 40bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * Redistribution and use in source and binary forms, with or without 50bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * modification, are permitted provided that the following conditions are 60bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * met: 70bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * 80bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * * Redistributions of source code must retain the above copyright 90bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * notice, this list of conditions and the following disclaimer. 100bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * * Redistributions in binary form must reproduce the above 110bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * copyright notice, this list of conditions and the following disclaimer 120bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * in the documentation and/or other materials provided with the 130bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * distribution. 140bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * * Neither the name of Google Inc. nor the names of its 150bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * contributors may be used to endorse or promote products derived from 160bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * this software without specific prior written permission. 170bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * 180bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 190bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 200bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 210bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 220bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 230bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 240bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 250bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 260bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 270bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 280bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 290bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch */ 300bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 310bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#ifndef DOMData_h 320bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#define DOMData_h 330bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 340bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#include "DOMDataStore.h" 35dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block#include "V8DOMWrapper.h" 360bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 370bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdochnamespace WebCore { 380bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 390bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // DOMData 400bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // 410bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // DOMData represents the all the DOM wrappers for a given thread. In 420bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // particular, DOMData holds wrappers for all the isolated worlds in the 430bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // thread. The DOMData for the main thread and the DOMData for child threads 440bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // use different subclasses. 450bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // 46ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch class DOMData { 47ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch WTF_MAKE_NONCOPYABLE(DOMData); 480bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch public: 490bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch DOMData(); 505f53aa361c2190e849eaea8aa53984acbc4cc63fAndrei Popescu virtual ~DOMData(); 510bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 520bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch static DOMData* getCurrent(); 530bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch virtual DOMDataStore& getStore() = 0; 540bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 550bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch template<typename T> 56d0825bca7fe65beaee391d30da42e937db621564Steve Block static void handleWeakObject(DOMDataStore::DOMWrapperMapType, v8::Persistent<v8::Object>, T* domObject); 570bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 580bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch template<typename T> 59f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch static void removeObjectsFromWrapperMap(DOMDataStore* store, AbstractWeakReferenceMap<T, v8::Object>& domMap); 600bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 610bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch ThreadIdentifier owningThread() const { return m_owningThread; } 620bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 630bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch private: 64dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block static void derefObject(WrapperTypeInfo* type, void* domObject); 650bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 66d0825bca7fe65beaee391d30da42e937db621564Steve Block template<typename T> 67d0825bca7fe65beaee391d30da42e937db621564Steve Block class WrapperMapObjectRemover : public WeakReferenceMap<T, v8::Object>::Visitor { 68d0825bca7fe65beaee391d30da42e937db621564Steve Block public: 69f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch virtual void visitDOMWrapper(DOMDataStore* store, T* domObject, v8::Persistent<v8::Object> v8Object) 70d0825bca7fe65beaee391d30da42e937db621564Steve Block { 71dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block WrapperTypeInfo* type = V8DOMWrapper::domWrapperType(v8Object); 72d0825bca7fe65beaee391d30da42e937db621564Steve Block derefObject(type, domObject); 73d0825bca7fe65beaee391d30da42e937db621564Steve Block v8Object.Dispose(); 74d0825bca7fe65beaee391d30da42e937db621564Steve Block } 75d0825bca7fe65beaee391d30da42e937db621564Steve Block }; 76d0825bca7fe65beaee391d30da42e937db621564Steve Block 770bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch ThreadIdentifier m_owningThread; 780bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch }; 790bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 800bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch template<typename T> 81d0825bca7fe65beaee391d30da42e937db621564Steve Block void DOMData::handleWeakObject(DOMDataStore::DOMWrapperMapType mapType, v8::Persistent<v8::Object> v8Object, T* domObject) 820bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch { 83967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch WrapperTypeInfo* type = V8DOMWrapper::domWrapperType(v8Object); 840bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch DOMDataList& list = DOMDataStore::allStores(); 85967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch bool found = false; 860bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch for (size_t i = 0; i < list.size(); ++i) { 870bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch DOMDataStore* store = list[i]; 88dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block ASSERT(store->domData()->owningThread() == WTF::currentThread()); 890bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 90dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block DOMWrapperMap<T>* domMap = static_cast<DOMWrapperMap<T>*>(store->getDOMWrapperMap(mapType)); 91967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch if (domMap->removeIfPresent(domObject, v8Object)) { 92967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch derefObject(type, domObject); 93967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch found = true; 94967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch } 95967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch } 96967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch 97967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch // If not found, it means map for the wrapper has been already destroyed, just dispose the 98967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch // handle and deref the object to fight memory leak. 99967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch if (!found) { 100967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch v8Object.Dispose(); 101967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch derefObject(type, domObject); 1020bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch } 1030bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch } 1040bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 1050bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch template<typename T> 106f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch void DOMData::removeObjectsFromWrapperMap(DOMDataStore* store, AbstractWeakReferenceMap<T, v8::Object>& domMap) 1070bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch { 108d0825bca7fe65beaee391d30da42e937db621564Steve Block WrapperMapObjectRemover<T> remover; 109f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch domMap.visit(store, &remover); 110d0825bca7fe65beaee391d30da42e937db621564Steve Block domMap.clear(); 1110bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch } 1120bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 1130bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch} // namespace WebCore 1140bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 1150bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#endif // DOMData_h 116