1 /*
2 * Copyright (C) 2010 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 "DownloadProxy.h"
28
29 #include "AuthenticationChallengeProxy.h"
30 #include "DataReference.h"
31 #include "WebContext.h"
32 #include "WebData.h"
33 #include "WebProcessMessages.h"
34 #include <wtf/text/CString.h>
35 #include <wtf/text/WTFString.h>
36
37 using namespace WebCore;
38
39 namespace WebKit {
40
generateDownloadID()41 static uint64_t generateDownloadID()
42 {
43 static uint64_t uniqueDownloadID = 0;
44 return ++uniqueDownloadID;
45 }
46
create(WebContext * webContext)47 PassRefPtr<DownloadProxy> DownloadProxy::create(WebContext* webContext)
48 {
49 return adoptRef(new DownloadProxy(webContext));
50 }
51
DownloadProxy(WebContext * webContext)52 DownloadProxy::DownloadProxy(WebContext* webContext)
53 : m_webContext(webContext)
54 , m_downloadID(generateDownloadID())
55 {
56 }
57
~DownloadProxy()58 DownloadProxy::~DownloadProxy()
59 {
60 ASSERT(!m_webContext);
61 }
62
cancel()63 void DownloadProxy::cancel()
64 {
65 if (!m_webContext)
66 return;
67
68 // FIXME (Multi-WebProcess): Downloads shouldn't be handled in the web process.
69 m_webContext->sendToAllProcesses(Messages::WebProcess::CancelDownload(m_downloadID));
70 }
71
invalidate()72 void DownloadProxy::invalidate()
73 {
74 ASSERT(m_webContext);
75 m_webContext = 0;
76 }
77
processDidClose()78 void DownloadProxy::processDidClose()
79 {
80 if (!m_webContext)
81 return;
82
83 m_webContext->downloadClient().processDidCrash(m_webContext, this);
84 }
85
didStart(const ResourceRequest & request)86 void DownloadProxy::didStart(const ResourceRequest& request)
87 {
88 m_request = request;
89
90 if (!m_webContext)
91 return;
92
93 m_webContext->downloadClient().didStart(m_webContext, this);
94 }
95
didReceiveAuthenticationChallenge(const AuthenticationChallenge & authenticationChallenge,uint64_t challengeID)96 void DownloadProxy::didReceiveAuthenticationChallenge(const AuthenticationChallenge& authenticationChallenge, uint64_t challengeID)
97 {
98 if (!m_webContext)
99 return;
100
101 RefPtr<AuthenticationChallengeProxy> authenticationChallengeProxy = AuthenticationChallengeProxy::create(authenticationChallenge, challengeID, m_webContext->process());
102 m_webContext->downloadClient().didReceiveAuthenticationChallenge(m_webContext, this, authenticationChallengeProxy.get());
103 }
104
didReceiveResponse(const ResourceResponse & response)105 void DownloadProxy::didReceiveResponse(const ResourceResponse& response)
106 {
107 if (!m_webContext)
108 return;
109
110 m_webContext->downloadClient().didReceiveResponse(m_webContext, this, response);
111 }
112
didReceiveData(uint64_t length)113 void DownloadProxy::didReceiveData(uint64_t length)
114 {
115 if (!m_webContext)
116 return;
117
118 m_webContext->downloadClient().didReceiveData(m_webContext, this, length);
119 }
120
shouldDecodeSourceDataOfMIMEType(const String & mimeType,bool & result)121 void DownloadProxy::shouldDecodeSourceDataOfMIMEType(const String& mimeType, bool& result)
122 {
123 if (!m_webContext)
124 return;
125
126 result = m_webContext->downloadClient().shouldDecodeSourceDataOfMIMEType(m_webContext, this, mimeType);
127 }
128
decideDestinationWithSuggestedFilename(const String & filename,String & destination,bool & allowOverwrite,SandboxExtension::Handle & sandboxExtensionHandle)129 void DownloadProxy::decideDestinationWithSuggestedFilename(const String& filename, String& destination, bool& allowOverwrite, SandboxExtension::Handle& sandboxExtensionHandle)
130 {
131 if (!m_webContext)
132 return;
133
134 destination = m_webContext->downloadClient().decideDestinationWithSuggestedFilename(m_webContext, this, filename, allowOverwrite);
135
136 if (!destination.isNull())
137 SandboxExtension::createHandle(destination, SandboxExtension::WriteOnly, sandboxExtensionHandle);
138 }
139
didCreateDestination(const String & path)140 void DownloadProxy::didCreateDestination(const String& path)
141 {
142 if (!m_webContext)
143 return;
144
145 m_webContext->downloadClient().didCreateDestination(m_webContext, this, path);
146 }
147
didFinish()148 void DownloadProxy::didFinish()
149 {
150 if (!m_webContext)
151 return;
152
153 m_webContext->downloadClient().didFinish(m_webContext, this);
154
155 // This can cause the DownloadProxy object to be deleted.
156 m_webContext->downloadFinished(this);
157 }
158
createWebData(const CoreIPC::DataReference & data)159 static PassRefPtr<WebData> createWebData(const CoreIPC::DataReference& data)
160 {
161 if (data.isEmpty())
162 return 0;
163
164 return WebData::create(data.data(), data.size());
165 }
166
didFail(const ResourceError & error,const CoreIPC::DataReference & resumeData)167 void DownloadProxy::didFail(const ResourceError& error, const CoreIPC::DataReference& resumeData)
168 {
169 if (!m_webContext)
170 return;
171
172 m_resumeData = createWebData(resumeData);
173
174 m_webContext->downloadClient().didFail(m_webContext, this, error);
175
176 // This can cause the DownloadProxy object to be deleted.
177 m_webContext->downloadFinished(this);
178 }
179
didCancel(const CoreIPC::DataReference & resumeData)180 void DownloadProxy::didCancel(const CoreIPC::DataReference& resumeData)
181 {
182 m_resumeData = createWebData(resumeData);
183
184 m_webContext->downloadClient().didCancel(m_webContext, this);
185
186 // This can cause the DownloadProxy object to be deleted.
187 m_webContext->downloadFinished(this);
188 }
189
190 } // namespace WebKit
191
192