2 * Copyright (C) 2007 Apple Inc. All rights reserved.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
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.
13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 #include "ResourceError.h"
29 #if USE(CFURLCONNECTION)
32 #include <CoreFoundation/CFError.h>
33 #include <CFNetwork/CFNetworkErrors.h>
34 #include <WebKitSystemInterface/WebKitSystemInterface.h>
35 #include <wtf/RetainPtr.h>
39 ResourceError::ResourceError(CFErrorRef cfError)
40 : ResourceErrorBase(Type::Null)
41 , m_dataIsUpToDate(false)
42 , m_platformError(cfError)
45 setType((CFErrorGetCode(m_platformError.get()) == kCFURLErrorTimedOut) ? Type::Timeout : Type::General);
48 ResourceError::ResourceError(const String& domain, int errorCode, const URL& failingURL, const String& localizedDescription, CFDataRef certificate)
49 : ResourceErrorBase(domain, errorCode, failingURL, localizedDescription, Type::General)
50 , m_dataIsUpToDate(true)
51 , m_certificate(certificate)
55 PCCERT_CONTEXT ResourceError::certificate() const
60 return reinterpret_cast<PCCERT_CONTEXT>(CFDataGetBytePtr(m_certificate.get()));
63 void ResourceError::setCertificate(CFDataRef certificate)
65 m_certificate = certificate;
68 const CFStringRef failingURLStringKey = CFSTR("NSErrorFailingURLStringKey");
69 const CFStringRef failingURLKey = CFSTR("NSErrorFailingURLKey");
71 void ResourceError::platformLazyInit()
79 CFStringRef domain = CFErrorGetDomain(m_platformError.get());
80 if (domain == kCFErrorDomainMach || domain == kCFErrorDomainCocoa)
81 m_domain ="NSCustomErrorDomain";
82 else if (domain == kCFErrorDomainCFNetwork)
83 m_domain = "CFURLErrorDomain";
84 else if (domain == kCFErrorDomainPOSIX)
85 m_domain = "NSPOSIXErrorDomain";
86 else if (domain == kCFErrorDomainOSStatus)
87 m_domain = "NSOSStatusErrorDomain";
88 else if (domain == kCFErrorDomainWinSock)
89 m_domain = "kCFErrorDomainWinSock";
93 m_errorCode = CFErrorGetCode(m_platformError.get());
95 RetainPtr<CFDictionaryRef> userInfo = adoptCF(CFErrorCopyUserInfo(m_platformError.get()));
97 CFStringRef failingURLString = (CFStringRef) CFDictionaryGetValue(userInfo.get(), failingURLStringKey);
99 m_failingURL = URL(URL(), failingURLString);
101 CFURLRef failingURL = (CFURLRef) CFDictionaryGetValue(userInfo.get(), failingURLKey);
103 if (RetainPtr<CFURLRef> absoluteURLRef = adoptCF(CFURLCopyAbsoluteURL(failingURL)))
104 m_failingURL = URL(absoluteURLRef.get());
107 m_localizedDescription = (CFStringRef) CFDictionaryGetValue(userInfo.get(), kCFErrorLocalizedDescriptionKey);
109 m_certificate = wkGetSSLPeerCertificateData(userInfo.get());
112 m_dataIsUpToDate = true;
116 void ResourceError::doPlatformIsolatedCopy(const ResourceError& other)
118 m_certificate = other.m_certificate;
121 bool ResourceError::platformCompare(const ResourceError& a, const ResourceError& b)
123 return a.cfError() == b.cfError();
126 CFErrorRef ResourceError::cfError() const
129 ASSERT(!m_platformError);
133 if (!m_platformError) {
134 RetainPtr<CFMutableDictionaryRef> userInfo = adoptCF(CFDictionaryCreateMutable(0, 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks));
136 if (!m_localizedDescription.isEmpty())
137 CFDictionarySetValue(userInfo.get(), kCFErrorLocalizedDescriptionKey, m_localizedDescription.createCFString().get());
139 if (!m_failingURL.isEmpty()) {
140 RetainPtr<CFStringRef> failingURLString = m_failingURL.string().createCFString();
141 CFDictionarySetValue(userInfo.get(), failingURLStringKey, failingURLString.get());
142 if (RetainPtr<CFURLRef> url = m_failingURL.createCFURL())
143 CFDictionarySetValue(userInfo.get(), failingURLKey, url.get());
147 wkSetSSLPeerCertificateData(userInfo.get(), m_certificate.get());
149 m_platformError = adoptCF(CFErrorCreate(0, m_domain.createCFString().get(), m_errorCode, userInfo.get()));
152 return m_platformError.get();
155 ResourceError::operator CFErrorRef() const
160 // FIXME: Once <rdar://problem/5050841> is fixed we can remove this constructor.
161 ResourceError::ResourceError(CFStreamError error)
162 : ResourceErrorBase(Type::General)
163 , m_dataIsUpToDate(true)
165 m_errorCode = error.error;
167 switch(error.domain) {
168 case kCFStreamErrorDomainCustom:
169 m_domain ="NSCustomErrorDomain";
171 case kCFStreamErrorDomainPOSIX:
172 m_domain = "NSPOSIXErrorDomain";
174 case kCFStreamErrorDomainMacOSStatus:
175 m_domain = "NSOSStatusErrorDomain";
180 CFStreamError ResourceError::cfStreamError() const
184 CFStreamError result;
185 result.error = m_errorCode;
187 if (m_domain == "NSCustomErrorDomain")
188 result.domain = kCFStreamErrorDomainCustom;
189 else if (m_domain == "NSPOSIXErrorDomain")
190 result.domain = kCFStreamErrorDomainPOSIX;
191 else if (m_domain == "NSOSStatusErrorDomain")
192 result.domain = kCFStreamErrorDomainMacOSStatus;
194 result.domain = kCFStreamErrorDomainCustom;
195 ASSERT_NOT_REACHED();
201 ResourceError::operator CFStreamError() const
203 return cfStreamError();
206 } // namespace WebCore
208 #endif // USE(CFURLCONNECTION)