Changeset 222521 in webkit
- Timestamp:
- Sep 26, 2017 1:48:02 PM (7 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 1 added
- 9 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r222519 r222521 1 2017-09-26 Basuke Suzuki <Basuke.Suzuki@sony.com> 2 3 [Curl] Introduce CurlResponse to hold response information among threads. 4 https://bugs.webkit.org/show_bug.cgi?id=177496 5 6 Reviewed by Alex Christensen. 7 8 * platform/network/curl/AuthenticationChallenge.h: 9 * platform/network/curl/AuthenticationChallengeCurl.cpp: 10 (WebCore::AuthenticationChallenge::AuthenticationChallenge): 11 (WebCore::AuthenticationChallenge::protectionSpaceFromHandle): 12 * platform/network/curl/CurlContext.cpp: 13 (WebCore::CurlHandle::getHttpConnectCode): 14 * platform/network/curl/CurlContext.h: 15 * platform/network/curl/CurlResponse.h: Added. 16 (WebCore::CurlResponse::isolatedCopy const): 17 * platform/network/curl/ResourceHandleCurlDelegate.cpp: 18 (WebCore::ResourceHandleCurlDelegate::didReceiveAllHeaders): 19 (WebCore::ResourceHandleCurlDelegate::didReceiveContentData): 20 (WebCore::ResourceHandleCurlDelegate::handleLocalReceiveResponse): 21 (WebCore::ResourceHandleCurlDelegate::didFinish): 22 (WebCore::ResourceHandleCurlDelegate::handleDataURL): 23 (WebCore::ResourceHandleCurlDelegate::didReceiveHeader): 24 (WebCore::isHttpInfo): Deleted. 25 * platform/network/curl/ResourceHandleCurlDelegate.h: 26 * platform/network/curl/ResourceResponse.h: 27 (WebCore::ResourceResponse::ResourceResponse): 28 (WebCore::ResourceResponse::setResponseFired): Deleted. 29 (WebCore::ResourceResponse::responseFired): Deleted. 30 * platform/network/curl/ResourceResponseCurl.cpp: 31 (WebCore::ResourceResponse::ResourceResponse): 32 (WebCore::ResourceResponse::appendHTTPHeaderField): 33 (WebCore::ResourceResponse::setStatusLine): 34 1 35 2017-09-26 Chris Dumez <cdumez@apple.com> 2 36 -
trunk/Source/WebCore/platform/network/curl/AuthenticationChallenge.h
r222223 r222521 32 32 namespace WebCore { 33 33 34 class CurlResponse; 35 34 36 class AuthenticationChallenge final : public AuthenticationChallengeBase { 35 37 public: … … 43 45 } 44 46 45 AuthenticationChallenge( uint16_t, long, unsigned, const ResourceResponse&, AuthenticationClient* = nullptr);47 AuthenticationChallenge(const CurlResponse&, unsigned, const ResourceResponse&, AuthenticationClient* = nullptr); 46 48 AuthenticationClient* authenticationClient() const { return m_authenticationClient.get(); } 47 49 48 50 private: 49 51 ProtectionSpaceServerType protectionSpaceServerTypeFromURI(const URL&); 50 ProtectionSpace protectionSpaceFromHandle( uint16_t, long, const ResourceResponse&);52 ProtectionSpace protectionSpaceFromHandle(const CurlResponse&, const ResourceResponse&); 51 53 void removeLeadingAndTrailingQuotes(String&); 52 54 -
trunk/Source/WebCore/platform/network/curl/AuthenticationChallengeCurl.cpp
r222223 r222521 30 30 31 31 #include "CurlContext.h" 32 #include "CurlResponse.h" 32 33 #include "ResourceError.h" 33 34 34 35 namespace WebCore { 35 36 36 AuthenticationChallenge::AuthenticationChallenge( uint16_t connectPort, long availableHttpAuth, unsigned previousFailureCount, const ResourceResponse& response, AuthenticationClient* client)37 : AuthenticationChallengeBase(protectionSpaceFromHandle(c onnectPort, availableHttpAuth, response), Credential(), previousFailureCount, response, ResourceError())37 AuthenticationChallenge::AuthenticationChallenge(const CurlResponse& curlResponse, unsigned previousFailureCount, const ResourceResponse& response, AuthenticationClient* client) 38 : AuthenticationChallengeBase(protectionSpaceFromHandle(curlResponse, response), Credential(), previousFailureCount, response, ResourceError()) 38 39 , m_authenticationClient(client) 39 40 { … … 51 52 } 52 53 53 ProtectionSpace AuthenticationChallenge::protectionSpaceFromHandle( uint16_t connectPort, long availableHttpAuth, const ResourceResponse& response)54 ProtectionSpace AuthenticationChallenge::protectionSpaceFromHandle(const CurlResponse& curlResponse, const ResourceResponse& response) 54 55 { 56 auto port = curlResponse.connectPort; 57 auto availableHttpAuth = curlResponse.availableHttpAuth; 58 55 59 ProtectionSpaceAuthenticationScheme scheme = ProtectionSpaceAuthenticationSchemeUnknown; 56 60 if (availableHttpAuth & CURLAUTH_BASIC) … … 73 77 } 74 78 75 return ProtectionSpace(response.url().host(), static_cast<int>( connectPort), protectionSpaceServerTypeFromURI(response.url()), realm, scheme);79 return ProtectionSpace(response.url().host(), static_cast<int>(port), protectionSpaceServerTypeFromURI(response.url()), realm, scheme); 76 80 } 77 81 -
trunk/Source/WebCore/platform/network/curl/CurlContext.cpp
r222508 r222521 581 581 } 582 582 583 std::optional<long> CurlHandle::getHttpConnectCode() 584 { 585 if (!m_handle) 586 return std::nullopt; 587 588 long httpConnectCode; 589 CURLcode errorCode = curl_easy_getinfo(m_handle, CURLINFO_HTTP_CONNECTCODE, &httpConnectCode); 590 if (errorCode != CURLE_OK) 591 return std::nullopt; 592 593 return httpConnectCode; 594 } 595 583 596 std::optional<long long> CurlHandle::getContentLength() 584 597 { -
trunk/Source/WebCore/platform/network/curl/CurlContext.h
r222508 r222521 279 279 std::optional<uint16_t> getPrimaryPort(); 280 280 std::optional<long> getResponseCode(); 281 std::optional<long> getHttpConnectCode(); 281 282 std::optional<long long> getContentLength(); 282 283 std::optional<long> getHttpAuthAvail(); -
trunk/Source/WebCore/platform/network/curl/ResourceHandleCurlDelegate.cpp
r222511 r222521 318 318 } 319 319 320 inline static bool isHttpInfo(int statusCode) 321 { 322 return 100 <= statusCode && statusCode < 200; 323 } 324 325 void ResourceHandleCurlDelegate::didReceiveAllHeaders(URL url, long httpCode, long long contentLength, uint16_t connectPort, long availableHttpAuth) 320 void ResourceHandleCurlDelegate::didReceiveAllHeaders(const CurlResponse& receivedResponse) 326 321 { 327 322 ASSERT(isMainThread()); 328 323 329 response().setURL(url); 330 response().setExpectedContentLength(contentLength); 331 response().setHTTPStatusCode(httpCode); 332 response().setMimeType(extractMIMETypeFromMediaType(response().httpHeaderField(HTTPHeaderName::ContentType)).convertToASCIILowercase()); 333 response().setTextEncodingName(extractCharsetFromMediaType(response().httpHeaderField(HTTPHeaderName::ContentType))); 324 m_handle->getInternal()->m_response = ResourceResponse(receivedResponse); 334 325 335 326 if (response().isMultipart()) { … … 357 348 } 358 349 } else if (response().isUnauthorized()) { 359 AuthenticationChallenge challenge( connectPort, availableHttpAuth, m_authFailureCount, response(), m_handle);350 AuthenticationChallenge challenge(receivedResponse, m_authFailureCount, response(), m_handle); 360 351 m_handle->didReceiveAuthenticationChallenge(challenge); 361 352 m_authFailureCount++; … … 363 354 } 364 355 365 response().setResponseFired(true);356 m_didNotifyResponse = true; 366 357 367 358 if (m_handle->client()) { … … 384 375 ASSERT(isMainThread()); 385 376 386 if (! response().responseFired())377 if (!m_didNotifyResponse) 387 378 handleLocalReceiveResponse(); 388 379 … … 410 401 // Determine the MIME type based on the path. 411 402 response().setMimeType(MIMETypeRegistry::getMIMETypeForPath(url)); 412 response().setResponseFired(true); 403 404 m_didNotifyResponse = true; 405 413 406 if (m_handle->client()) 414 407 m_handle->client()->didReceiveResponse(m_handle, ResourceResponse(response())); … … 446 439 return; 447 440 448 if (! response().responseFired()) {441 if (!m_didNotifyResponse) { 449 442 handleLocalReceiveResponse(); 450 443 if (!m_handle) … … 479 472 ASSERT(m_handle->client()); 480 473 481 intindex = url.find(',');482 if (index == -1) {474 auto index = url.find(','); 475 if (index == notFound) { 483 476 m_handle->client()->cannotShowURL(m_handle); 484 477 return; … … 672 665 size_t ResourceHandleCurlDelegate::didReceiveHeader(String&& header) 673 666 { 667 static const auto emptyLineCRLF = "\r\n"; 668 static const auto emptyLineLF = "\n"; 669 674 670 if (!m_handle) 675 671 return 0; … … 678 674 return 0; 679 675 680 /* 681 * a) We can finish and send the ResourceResponse 682 * b) We will add the current header to the HTTPHeaderMap of the ResourceResponse 683 * 684 * The HTTP standard requires to use \r\n but for compatibility it recommends to 685 * accept also \n. 686 */ 687 if (header == AtomicString("\r\n") || header == AtomicString("\n")) { 688 long httpCode = 0; 689 if (auto code = m_curlHandle->getResponseCode()) 690 httpCode = *code; 691 692 if (!httpCode) { 693 // Comes here when receiving 200 Connection Established. Just return. 694 return header.length(); 695 } 696 697 if (isHttpInfo(httpCode)) { 698 // Just return when receiving http info, e.g. HTTP/1.1 100 Continue. 699 // If not, the request might be cancelled, because the MIME type will be empty for this response. 700 return header.length(); 701 } 702 703 URL url = m_curlHandle->getEffectiveURL(); 704 705 long long contentLength = 0; 706 if (auto length = m_curlHandle->getContentLength()) 707 contentLength = *length; 708 709 uint16_t connectPort = 0; 710 if (auto port = m_curlHandle->getPrimaryPort()) 711 connectPort = *port; 712 713 long availableAuth = CURLAUTH_NONE; 714 if (auto auth = m_curlHandle->getHttpAuthAvail()) 715 availableAuth = *auth; 716 717 if (isMainThread()) 718 didReceiveAllHeaders(url, httpCode, contentLength, connectPort, availableAuth); 719 else { 720 callOnMainThread([protectedThis = makeRef(*this), copyUrl = url.isolatedCopy(), httpCode, contentLength, connectPort, availableAuth] { 721 if (!protectedThis->m_handle) 722 return; 723 protectedThis->didReceiveAllHeaders(copyUrl, httpCode, contentLength, connectPort, availableAuth); 724 }); 725 } 726 } else { 727 // If the FOLLOWLOCATION option is enabled for the curl handle then 728 // curl will follow the redirections internally. Thus this header callback 729 // will be called more than one time with the line starting "HTTP" for one job. 730 if (isMainThread()) 731 response().appendHTTPHeaderField(header); 732 else { 733 callOnMainThread([protectedThis = makeRef(*this), copyHeader = header.isolatedCopy() ] { 734 if (!protectedThis->m_handle) 735 return; 736 737 protectedThis->response().appendHTTPHeaderField(copyHeader); 738 }); 739 } 740 } 741 742 return header.length(); 676 size_t receiveBytes = header.length(); 677 678 // The HTTP standard requires to use \r\n but for compatibility it recommends to accept also \n. 679 // We will add the current header to the CurlResponse.headers 680 if ((header != emptyLineCRLF) && (header != emptyLineLF)) { 681 m_response.headers.append(WTFMove(header)); 682 return receiveBytes; 683 } 684 685 // We can finish and send the ResourceResponse 686 long statusCode = 0; 687 if (auto code = m_curlHandle->getResponseCode()) 688 statusCode = *code; 689 690 long httpConnectCode = 0; 691 if (auto code = m_curlHandle->getHttpConnectCode()) 692 httpConnectCode = *code; 693 694 if ((100 <= statusCode) && (statusCode < 200)) { 695 // Just return when receiving http info, e.g. HTTP/1.1 100 Continue. 696 // If not, the request might be cancelled, because the MIME type will be empty for this response. 697 m_response = CurlResponse(); 698 return receiveBytes; 699 } 700 701 if (!statusCode && (httpConnectCode == 200)) { 702 // Comes here when receiving 200 Connection Established. Just return. 703 m_response = CurlResponse(); 704 return receiveBytes; 705 } 706 707 // If the FOLLOWLOCATION option is enabled for the curl handle then 708 // curl will follow the redirections internally. Thus this header callback 709 // will be called more than one time with the line starting "HTTP" for one job. 710 711 m_response.url = m_curlHandle->getEffectiveURL(); 712 m_response.statusCode = statusCode; 713 714 if (auto length = m_curlHandle->getContentLength()) 715 m_response.expectedContentLength = *length; 716 717 if (auto port = m_curlHandle->getPrimaryPort()) 718 m_response.connectPort = *port; 719 720 if (auto auth = m_curlHandle->getHttpAuthAvail()) 721 m_response.availableHttpAuth = *auth; 722 723 if (isMainThread()) 724 didReceiveAllHeaders(m_response); 725 else { 726 callOnMainThread([protectedThis = makeRef(*this), response = m_response.isolatedCopy()] { 727 if (!protectedThis->m_handle) 728 return; 729 protectedThis->didReceiveAllHeaders(response); 730 }); 731 } 732 733 return receiveBytes; 743 734 } 744 735 -
trunk/Source/WebCore/platform/network/curl/ResourceHandleCurlDelegate.h
r222511 r222521 31 31 #include "Credential.h" 32 32 #include "CurlJobManager.h" 33 #include "CurlResponse.h" 33 34 #include "CurlSSLVerifier.h" 34 35 #include "FormDataStreamCurl.h" … … 78 79 void setupAuthentication(); 79 80 80 void didReceiveAllHeaders( URL, long httpCode, long long contentLength, uint16_t connectPort, long availableHttpAuth);81 void didReceiveAllHeaders(const CurlResponse&); 81 82 void didReceiveContentData(Ref<SharedBuffer>&&); 82 83 void handleLocalReceiveResponse(); … … 123 124 std::unique_ptr<CurlHandle> m_curlHandle; 124 125 CurlSSLVerifier m_sslVerifier; 126 CurlResponse m_response; 127 bool m_didNotifyResponse { false }; 125 128 // Used by both threads. 126 129 bool m_isSyncRequest { false }; -
trunk/Source/WebCore/platform/network/curl/ResourceResponse.h
r222068 r222521 33 33 namespace WebCore { 34 34 35 class CurlResponse; 36 35 37 class ResourceResponse : public ResourceResponseBase { 36 38 public: 37 39 ResourceResponse() 38 : m_responseFired(false)40 : ResourceResponseBase() 39 41 { 40 42 } 41 43 42 44 ResourceResponse(const URL& url, const String& mimeType, long long expectedLength, const String& textEncodingName) 43 : ResourceResponseBase(url, mimeType, expectedLength, textEncodingName), 44 m_responseFired(false) 45 : ResourceResponseBase(url, mimeType, expectedLength, textEncodingName) 45 46 { 46 47 } 47 48 48 void setResponseFired(bool fired) { m_responseFired = fired; } 49 bool responseFired() { return m_responseFired; } 49 ResourceResponse(const CurlResponse&); 50 50 51 51 void appendHTTPHeaderField(const String&); … … 67 67 68 68 void setStatusLine(const String&); 69 70 bool m_responseFired;71 69 }; 72 70 -
trunk/Source/WebCore/platform/network/curl/ResourceResponseCurl.cpp
r222012 r222521 29 29 #include "ResourceResponse.h" 30 30 31 #include "CurlResponse.h" 31 32 #include "HTTPParsers.h" 32 33 … … 76 77 } 77 78 79 ResourceResponse::ResourceResponse(const CurlResponse& response) 80 : ResourceResponseBase(response.url, "", response.expectedContentLength, "") 81 { 82 setHTTPStatusCode(response.statusCode); 83 84 for (auto header : response.headers) 85 appendHTTPHeaderField(header); 86 87 setMimeType(extractMIMETypeFromMediaType(httpHeaderField(HTTPHeaderName::ContentType)).convertToASCIILowercase()); 88 setTextEncodingName(extractCharsetFromMediaType(httpHeaderField(HTTPHeaderName::ContentType))); 89 } 90 78 91 void ResourceResponse::appendHTTPHeaderField(const String& header) 79 92 { 80 intsplitPosistion = header.find(":");93 auto splitPosistion = header.find(":"); 81 94 if (splitPosistion != notFound) { 82 Stringkey = header.left(splitPosistion).stripWhiteSpace();83 Stringvalue = header.substring(splitPosistion + 1).stripWhiteSpace();95 auto key = header.left(splitPosistion).stripWhiteSpace(); 96 auto value = header.substring(splitPosistion + 1).stripWhiteSpace(); 84 97 85 98 if (isAppendableHeader(key)) … … 95 108 void ResourceResponse::setStatusLine(const String& header) 96 109 { 97 StringstatusLine = header.stripWhiteSpace();110 auto statusLine = header.stripWhiteSpace(); 98 111 99 inthttpVersionEndPosition = statusLine.find(" ");100 intstatusCodeEndPosition = notFound;112 auto httpVersionEndPosition = statusLine.find(" "); 113 auto statusCodeEndPosition = notFound; 101 114 102 115 // Extract the http version 103 116 if (httpVersionEndPosition != notFound) { 104 StringhttpVersion = statusLine.left(httpVersionEndPosition);117 auto httpVersion = statusLine.left(httpVersionEndPosition); 105 118 setHTTPVersion(httpVersion.stripWhiteSpace()); 106 119 … … 111 124 // Extract the http status text 112 125 if (statusCodeEndPosition != notFound) { 113 StringstatusText = statusLine.substring(statusCodeEndPosition + 1);126 auto statusText = statusLine.substring(statusCodeEndPosition + 1); 114 127 setHTTPStatusText(statusText.stripWhiteSpace()); 115 128 }
Note: See TracChangeset
for help on using the changeset viewer.