1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254
|
/*
* Copyright (C) 2006, 2007, 2008, 2009, 2014 Apple Inc. All rights reserved.
* Copyright (C) 2007 Justin Haygood (jhaygood@reaktix.com)
*
* 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. ``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
* 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 IconDatabase_h
#define IconDatabase_h
#include "IconDatabaseBase.h"
#include <wtf/text/WTFString.h>
#if ENABLE(ICONDATABASE)
#include "SQLiteDatabase.h"
#include "Timer.h"
#include <wtf/HashCountedSet.h>
#include <wtf/HashMap.h>
#include <wtf/HashSet.h>
#endif
namespace WebCore {
#if !ENABLE(ICONDATABASE)
// Dummy version of IconDatabase that does nothing.
class IconDatabase final : public IconDatabaseBase {
WTF_MAKE_FAST_ALLOCATED;
public:
static void delayDatabaseCleanup() { }
static void allowDatabaseCleanup() { }
static void checkIntegrityBeforeOpening() { }
// FIXME: Is it really helpful to return a filename here rather than just the null string?
static String defaultDatabaseFilename() { return ASCIILiteral("WebpageIcons.db"); }
};
#else
class IconRecord;
class IconSnapshot;
class PageURLRecord;
class PageURLSnapshot;
class SuddenTerminationDisabler;
class IconDatabase final : public IconDatabaseBase {
WTF_MAKE_FAST_ALLOCATED;
// *** Main Thread Only ***
public:
WEBCORE_EXPORT IconDatabase();
~IconDatabase();
WEBCORE_EXPORT virtual void setClient(IconDatabaseClient*) override;
WEBCORE_EXPORT virtual bool open(const String& directory, const String& filename) override;
WEBCORE_EXPORT virtual void close() override;
WEBCORE_EXPORT virtual void removeAllIcons() override;
void readIconForPageURLFromDisk(const String&);
WEBCORE_EXPORT virtual Image* defaultIcon(const IntSize&) override;
WEBCORE_EXPORT virtual void retainIconForPageURL(const String&) override;
WEBCORE_EXPORT virtual void releaseIconForPageURL(const String&) override;
WEBCORE_EXPORT virtual void setIconDataForIconURL(PassRefPtr<SharedBuffer> data, const String&) override;
WEBCORE_EXPORT virtual void setIconURLForPageURL(const String& iconURL, const String& pageURL) override;
WEBCORE_EXPORT virtual Image* synchronousIconForPageURL(const String&, const IntSize&) override;
virtual PassNativeImagePtr synchronousNativeIconForPageURL(const String& pageURLOriginal, const IntSize&) override;
WEBCORE_EXPORT virtual String synchronousIconURLForPageURL(const String&) override;
virtual bool synchronousIconDataKnownForIconURL(const String&) override;
WEBCORE_EXPORT virtual IconLoadDecision synchronousLoadDecisionForIconURL(const String&, DocumentLoader*) override;
WEBCORE_EXPORT virtual void setEnabled(bool) override;
virtual bool isEnabled() const override;
WEBCORE_EXPORT virtual void setPrivateBrowsingEnabled(bool flag) override;
bool isPrivateBrowsingEnabled() const;
WEBCORE_EXPORT static void delayDatabaseCleanup();
WEBCORE_EXPORT static void allowDatabaseCleanup();
WEBCORE_EXPORT static void checkIntegrityBeforeOpening();
// Support for WebCoreStatistics in WebKit
WEBCORE_EXPORT virtual size_t pageURLMappingCount() override;
WEBCORE_EXPORT virtual size_t retainedPageURLCount() override;
WEBCORE_EXPORT virtual size_t iconRecordCount() override;
WEBCORE_EXPORT virtual size_t iconRecordCountWithData() override;
private:
friend IconDatabaseBase& iconDatabase();
void notifyPendingLoadDecisions();
void wakeSyncThread();
void scheduleOrDeferSyncTimer();
void syncTimerFired(Timer<IconDatabase>&);
Timer<IconDatabase> m_syncTimer;
ThreadIdentifier m_syncThread;
bool m_syncThreadRunning;
HashSet<RefPtr<DocumentLoader>> m_loadersPendingDecision;
RefPtr<IconRecord> m_defaultIconRecord;
bool m_scheduleOrDeferSyncTimerRequested;
std::unique_ptr<SuddenTerminationDisabler> m_disableSuddenTerminationWhileSyncTimerScheduled;
// *** Any Thread ***
public:
WEBCORE_EXPORT virtual bool isOpen() const;
WEBCORE_EXPORT virtual String databasePath() const;
WEBCORE_EXPORT static String defaultDatabaseFilename();
private:
PassRefPtr<IconRecord> getOrCreateIconRecord(const String& iconURL);
PageURLRecord* getOrCreatePageURLRecord(const String& pageURL);
WEBCORE_EXPORT bool m_isEnabled;
bool m_privateBrowsingEnabled;
mutable Mutex m_syncLock;
ThreadCondition m_syncCondition;
String m_databaseDirectory;
// Holding m_syncLock is required when accessing m_completeDatabasePath
String m_completeDatabasePath;
bool m_threadTerminationRequested;
bool m_removeIconsRequested;
bool m_iconURLImportComplete;
bool m_syncThreadHasWorkToDo;
std::unique_ptr<SuddenTerminationDisabler> m_disableSuddenTerminationWhileSyncThreadHasWorkToDo;
Mutex m_urlAndIconLock;
// Holding m_urlAndIconLock is required when accessing any of the following data structures or the objects they contain
HashMap<String, IconRecord*> m_iconURLToRecordMap;
HashMap<String, PageURLRecord*> m_pageURLToRecordMap;
HashSet<String> m_retainedPageURLs;
Mutex m_pendingSyncLock;
// Holding m_pendingSyncLock is required when accessing any of the following data structures
HashMap<String, PageURLSnapshot> m_pageURLsPendingSync;
HashMap<String, IconSnapshot> m_iconsPendingSync;
Mutex m_pendingReadingLock;
// Holding m_pendingSyncLock is required when accessing any of the following data structures - when dealing with IconRecord*s, holding m_urlAndIconLock is also required
HashSet<String> m_pageURLsPendingImport;
HashSet<String> m_pageURLsInterestedInIcons;
HashSet<IconRecord*> m_iconsPendingReading;
Mutex m_urlsToRetainOrReleaseLock;
// Holding m_urlsToRetainOrReleaseLock is required when accessing any of the following data structures.
HashCountedSet<String> m_urlsToRetain;
HashCountedSet<String> m_urlsToRelease;
bool m_retainOrReleaseIconRequested;
// *** Sync Thread Only ***
public:
WEBCORE_EXPORT virtual bool shouldStopThreadActivity() const;
private:
static void iconDatabaseSyncThreadStart(void *);
void iconDatabaseSyncThread();
// The following block of methods are called exclusively by the sync thread to manage i/o to and from the database
// Each method should periodically monitor m_threadTerminationRequested when it makes sense to return early on shutdown
void performOpenInitialization();
bool checkIntegrity();
void performURLImport();
void syncThreadMainLoop();
bool readFromDatabase();
bool writeToDatabase();
void pruneUnretainedIcons();
void checkForDanglingPageURLs(bool pruneIfFound);
void removeAllIconsOnThread();
void deleteAllPreparedStatements();
void* cleanupSyncThread();
void performRetainIconForPageURL(const String&, int retainCount);
void performReleaseIconForPageURL(const String&, int releaseCount);
bool wasExcludedFromBackup();
void setWasExcludedFromBackup();
bool isOpenBesidesMainThreadCallbacks() const;
void checkClosedAfterMainThreadCallback();
bool m_initialPruningComplete;
void setIconURLForPageURLInSQLDatabase(const String&, const String&);
void setIconIDForPageURLInSQLDatabase(int64_t, const String&);
void removePageURLFromSQLDatabase(const String& pageURL);
int64_t getIconIDForIconURLFromSQLDatabase(const String& iconURL);
int64_t addIconURLToSQLDatabase(const String&);
PassRefPtr<SharedBuffer> getImageDataForIconURLFromSQLDatabase(const String& iconURL);
void removeIconFromSQLDatabase(const String& iconURL);
void writeIconSnapshotToSQLDatabase(const IconSnapshot&);
void performPendingRetainAndReleaseOperations();
// Methods to dispatch client callbacks on the main thread
void dispatchDidImportIconURLForPageURLOnMainThread(const String&);
void dispatchDidImportIconDataForPageURLOnMainThread(const String&);
void dispatchDidRemoveAllIconsOnMainThread();
void dispatchDidFinishURLImportOnMainThread();
std::atomic<uint32_t> m_mainThreadCallbackCount;
// The client is set by the main thread before the thread starts, and from then on is only used by the sync thread
IconDatabaseClient* m_client;
SQLiteDatabase m_syncDB;
OwnPtr<SQLiteStatement> m_setIconIDForPageURLStatement;
OwnPtr<SQLiteStatement> m_removePageURLStatement;
OwnPtr<SQLiteStatement> m_getIconIDForIconURLStatement;
OwnPtr<SQLiteStatement> m_getImageDataForIconURLStatement;
OwnPtr<SQLiteStatement> m_addIconToIconInfoStatement;
OwnPtr<SQLiteStatement> m_addIconToIconDataStatement;
OwnPtr<SQLiteStatement> m_getImageDataStatement;
OwnPtr<SQLiteStatement> m_deletePageURLsForIconURLStatement;
OwnPtr<SQLiteStatement> m_deleteIconFromIconInfoStatement;
OwnPtr<SQLiteStatement> m_deleteIconFromIconDataStatement;
OwnPtr<SQLiteStatement> m_updateIconInfoStatement;
OwnPtr<SQLiteStatement> m_updateIconDataStatement;
OwnPtr<SQLiteStatement> m_setIconInfoStatement;
OwnPtr<SQLiteStatement> m_setIconDataStatement;
};
#endif // !ENABLE(ICONDATABASE)
} // namespace WebCore
#endif // IconDatabase_h
|