Add WTF::move()
[WebKit-https.git] / Source / WebCore / page / UserContentController.cpp
1 /*
2  * Copyright (C) 2014 Apple Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
14  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
15  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
17  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
18  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
19  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
20  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
21  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
22  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
23  * THE POSSIBILITY OF SUCH DAMAGE.
24  */
25
26 #include "config.h"
27 #include "UserContentController.h"
28
29 #include "DOMWrapperWorld.h"
30 #include "Document.h"
31 #include "MainFrame.h"
32 #include "Page.h"
33 #include "UserScript.h"
34 #include "UserStyleSheet.h"
35
36 #if ENABLE(USER_MESSAGE_HANDLERS)
37 #include "UserMessageHandlerDescriptor.h"
38 #endif
39
40 namespace WebCore {
41
42 RefPtr<UserContentController> UserContentController::create()
43 {
44     return adoptRef(new UserContentController);
45 }
46
47 UserContentController::UserContentController()
48 {
49 }
50
51 UserContentController::~UserContentController()
52 {
53 }
54
55 void UserContentController::addPage(Page& page)
56 {
57     ASSERT(!m_pages.contains(&page));
58     m_pages.add(&page);
59 }
60
61 void UserContentController::removePage(Page& page)
62 {
63     ASSERT(m_pages.contains(&page));
64     m_pages.remove(&page);
65 }
66
67 void UserContentController::addUserScript(DOMWrapperWorld& world, std::unique_ptr<UserScript> userScript)
68 {
69     if (!m_userScripts)
70         m_userScripts = std::make_unique<UserScriptMap>();
71
72     auto& scriptsInWorld = m_userScripts->add(&world, nullptr).iterator->value;
73     if (!scriptsInWorld)
74         scriptsInWorld = std::make_unique<UserScriptVector>();
75     scriptsInWorld->append(WTF::move(userScript));
76 }
77
78 void UserContentController::removeUserScript(DOMWrapperWorld& world, const URL& url)
79 {
80     if (!m_userScripts)
81         return;
82
83     auto it = m_userScripts->find(&world);
84     if (it == m_userScripts->end())
85         return;
86
87     auto scripts = it->value.get();
88     for (int i = scripts->size() - 1; i >= 0; --i) {
89         if (scripts->at(i)->url() == url)
90             scripts->remove(i);
91     }
92
93     if (scripts->isEmpty())
94         m_userScripts->remove(it);
95 }
96
97 void UserContentController::removeUserScripts(DOMWrapperWorld& world)
98 {
99     if (!m_userScripts)
100         return;
101
102     m_userScripts->remove(&world);
103 }
104
105 void UserContentController::addUserStyleSheet(DOMWrapperWorld& world, std::unique_ptr<UserStyleSheet> userStyleSheet, UserStyleInjectionTime injectionTime)
106 {
107     if (!m_userStyleSheets)
108         m_userStyleSheets = std::make_unique<UserStyleSheetMap>();
109
110     auto& styleSheetsInWorld = m_userStyleSheets->add(&world, nullptr).iterator->value;
111     if (!styleSheetsInWorld)
112         styleSheetsInWorld = std::make_unique<UserStyleSheetVector>();
113     styleSheetsInWorld->append(WTF::move(userStyleSheet));
114
115     if (injectionTime == InjectInExistingDocuments)
116         invalidateInjectedStyleSheetCacheInAllFrames();
117 }
118
119 void UserContentController::removeUserStyleSheet(DOMWrapperWorld& world, const URL& url)
120 {
121     if (!m_userStyleSheets)
122         return;
123
124     auto it = m_userStyleSheets->find(&world);
125     if (it == m_userStyleSheets->end())
126         return;
127
128     auto& stylesheets = *it->value;
129
130     bool sheetsChanged = false;
131     for (int i = stylesheets.size() - 1; i >= 0; --i) {
132         if (stylesheets[i]->url() == url) {
133             stylesheets.remove(i);
134             sheetsChanged = true;
135         }
136     }
137
138     if (!sheetsChanged)
139         return;
140
141     if (stylesheets.isEmpty())
142         m_userStyleSheets->remove(it);
143
144     invalidateInjectedStyleSheetCacheInAllFrames();
145 }
146
147 void UserContentController::removeUserStyleSheets(DOMWrapperWorld& world)
148 {
149     if (!m_userStyleSheets)
150         return;
151
152     if (!m_userStyleSheets->remove(&world))
153         return;
154
155     invalidateInjectedStyleSheetCacheInAllFrames();
156 }
157
158 #if ENABLE(USER_MESSAGE_HANDLERS)
159 void UserContentController::addUserMessageHandlerDescriptor(UserMessageHandlerDescriptor& descriptor)
160 {
161     if (!m_userMessageHandlerDescriptors)
162         m_userMessageHandlerDescriptors = std::make_unique<UserMessageHandlerDescriptorMap>();
163
164     m_userMessageHandlerDescriptors->add(std::make_pair(descriptor.name(), &descriptor.world()), &descriptor);
165 }
166
167 void UserContentController::removeUserMessageHandlerDescriptor(UserMessageHandlerDescriptor& descriptor)
168 {
169     if (!m_userMessageHandlerDescriptors)
170         return;
171
172     m_userMessageHandlerDescriptors->remove(std::make_pair(descriptor.name(), &descriptor.world()));
173 }
174 #endif
175
176 void UserContentController::removeAllUserContent()
177 {
178     m_userScripts = nullptr;
179
180     if (m_userStyleSheets) {
181         m_userStyleSheets = nullptr;
182         invalidateInjectedStyleSheetCacheInAllFrames();
183     }
184 }
185
186 void UserContentController::invalidateInjectedStyleSheetCacheInAllFrames()
187 {
188     for (auto& page : m_pages) {
189         for (Frame* frame = &page->mainFrame(); frame; frame = frame->tree().traverseNext()) {
190             frame->document()->styleSheetCollection().invalidateInjectedStyleSheetCache();
191             frame->document()->styleResolverChanged(DeferRecalcStyle);
192         }
193     }
194 }
195
196 } // namespace WebCore