OLD | NEW |
1 /* | 1 /* |
2 Copyright (C) 1998 Lars Knoll (knoll@mpi-hd.mpg.de) | 2 Copyright (C) 1998 Lars Knoll (knoll@mpi-hd.mpg.de) |
3 Copyright (C) 2001 Dirk Mueller (mueller@kde.org) | 3 Copyright (C) 2001 Dirk Mueller (mueller@kde.org) |
4 Copyright (C) 2002 Waldo Bastian (bastian@kde.org) | 4 Copyright (C) 2002 Waldo Bastian (bastian@kde.org) |
5 Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All | 5 Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All |
6 rights reserved. | 6 rights reserved. |
7 Copyright (C) 2009 Torch Mobile Inc. http://www.torchmobile.com/ | 7 Copyright (C) 2009 Torch Mobile Inc. http://www.torchmobile.com/ |
8 | 8 |
9 This library is free software; you can redistribute it and/or | 9 This library is free software; you can redistribute it and/or |
10 modify it under the terms of the GNU Library General Public | 10 modify it under the terms of the GNU Library General Public |
(...skipping 475 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
486 if (params.IsSpeculativePreload() || params.IsLinkPreload()) { | 486 if (params.IsSpeculativePreload() || params.IsLinkPreload()) { |
487 DEFINE_RESOURCE_HISTOGRAM("Preload."); | 487 DEFINE_RESOURCE_HISTOGRAM("Preload."); |
488 } else { | 488 } else { |
489 DEFINE_RESOURCE_HISTOGRAM(""); | 489 DEFINE_RESOURCE_HISTOGRAM(""); |
490 } | 490 } |
491 | 491 |
492 // Aims to count Resource only referenced from MemoryCache (i.e. what would be | 492 // Aims to count Resource only referenced from MemoryCache (i.e. what would be |
493 // dead if MemoryCache holds weak references to Resource). Currently we check | 493 // dead if MemoryCache holds weak references to Resource). Currently we check |
494 // references to Resource from ResourceClient and |m_preloads| only, because | 494 // references to Resource from ResourceClient and |m_preloads| only, because |
495 // they are major sources of references. | 495 // they are major sources of references. |
496 if (resource && !resource->IsAlive() && !ContainsAsPreload(resource)) { | 496 if (resource && !resource->IsAlive() && !preloads_.Contains(resource)) { |
497 DEFINE_RESOURCE_HISTOGRAM("Dead."); | 497 DEFINE_RESOURCE_HISTOGRAM("Dead."); |
498 } | 498 } |
499 } | 499 } |
500 | 500 |
501 bool ResourceFetcher::ContainsAsPreload(Resource* resource) const { | |
502 auto it = preloads_.find(PreloadKey(resource->Url(), resource->GetType())); | |
503 return it != preloads_.end() && it->value == resource; | |
504 } | |
505 | |
506 void ResourceFetcher::RemovePreload(Resource* resource) { | |
507 auto it = preloads_.find(PreloadKey(resource->Url(), resource->GetType())); | |
508 if (it == preloads_.end()) | |
509 return; | |
510 if (it->value == resource) { | |
511 resource->DecreasePreloadCount(); | |
512 preloads_.erase(it); | |
513 } | |
514 } | |
515 | |
516 ResourceFetcher::PrepareRequestResult ResourceFetcher::PrepareRequest( | 501 ResourceFetcher::PrepareRequestResult ResourceFetcher::PrepareRequest( |
517 FetchParameters& params, | 502 FetchParameters& params, |
518 const ResourceFactory& factory, | 503 const ResourceFactory& factory, |
519 const SubstituteData& substitute_data, | 504 const SubstituteData& substitute_data, |
520 unsigned long identifier, | 505 unsigned long identifier, |
521 ResourceRequestBlockedReason& blocked_reason) { | 506 ResourceRequestBlockedReason& blocked_reason) { |
522 ResourceRequest& resource_request = params.MutableResourceRequest(); | 507 ResourceRequest& resource_request = params.MutableResourceRequest(); |
523 | 508 |
524 DCHECK(params.Options().synchronous_policy == kRequestAsynchronously || | 509 DCHECK(params.Options().synchronous_policy == kRequestAsynchronously || |
525 factory.GetType() == Resource::kRaw || | 510 factory.GetType() == Resource::kRaw || |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
612 bool is_static_data = is_data_url || substitute_data.IsValid() || archive_; | 597 bool is_static_data = is_data_url || substitute_data.IsValid() || archive_; |
613 if (is_static_data) { | 598 if (is_static_data) { |
614 resource = ResourceForStaticData(params, factory, substitute_data); | 599 resource = ResourceForStaticData(params, factory, substitute_data); |
615 // Abort the request if the archive doesn't contain the resource, except in | 600 // Abort the request if the archive doesn't contain the resource, except in |
616 // the case of data URLs which might have resources such as fonts that need | 601 // the case of data URLs which might have resources such as fonts that need |
617 // to be decoded only on demand. These data URLs are allowed to be | 602 // to be decoded only on demand. These data URLs are allowed to be |
618 // processed using the normal ResourceFetcher machinery. | 603 // processed using the normal ResourceFetcher machinery. |
619 if (!resource && !is_data_url && archive_) | 604 if (!resource && !is_data_url && archive_) |
620 return nullptr; | 605 return nullptr; |
621 } | 606 } |
622 RevalidationPolicy policy = kLoad; | |
623 bool preload_found = false; | |
624 if (!resource) { | 607 if (!resource) { |
625 resource = MatchPreload(params, factory.GetType()); | 608 resource = |
626 if (resource) { | 609 GetMemoryCache()->ResourceForURL(params.Url(), GetCacheIdentifier()); |
627 preload_found = true; | |
628 policy = kUse; | |
629 // If |param| is for a blocking resource and a preloaded resource is | |
630 // found, we may need to make it block the onload event. | |
631 MakePreloadedResourceBlockOnloadIfNeeded(resource, params); | |
632 } | |
633 } | 610 } |
634 if (!preload_found) { | |
635 if (!resource) { | |
636 resource = | |
637 GetMemoryCache()->ResourceForURL(params.Url(), GetCacheIdentifier()); | |
638 } | |
639 | 611 |
640 policy = DetermineRevalidationPolicy(factory.GetType(), params, resource, | 612 // If we got a preloaded resource from the cache for a non-preload request, |
641 is_static_data); | 613 // we may need to make it block the onload event. |
642 TRACE_EVENT_INSTANT1( | 614 MakePreloadedResourceBlockOnloadIfNeeded(resource, params); |
643 "blink", "ResourceFetcher::determineRevalidationPolicy", | 615 |
644 TRACE_EVENT_SCOPE_THREAD, "revalidationPolicy", policy); | 616 const RevalidationPolicy policy = DetermineRevalidationPolicy( |
645 } | 617 factory.GetType(), params, resource, is_static_data); |
| 618 TRACE_EVENT_INSTANT1("blink", "ResourceFetcher::determineRevalidationPolicy", |
| 619 TRACE_EVENT_SCOPE_THREAD, "revalidationPolicy", policy); |
646 | 620 |
647 UpdateMemoryCacheStats(resource, policy, params, factory, is_static_data); | 621 UpdateMemoryCacheStats(resource, policy, params, factory, is_static_data); |
648 | 622 |
649 switch (policy) { | 623 switch (policy) { |
650 case kReload: | 624 case kReload: |
651 GetMemoryCache()->Remove(resource); | 625 GetMemoryCache()->Remove(resource); |
652 // Fall through | 626 // Fall through |
653 case kLoad: | 627 case kLoad: |
654 resource = CreateResourceForLoading(params, params.Charset(), factory); | 628 resource = CreateResourceForLoading(params, params.Charset(), factory); |
655 break; | 629 break; |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
688 // If only the fragment identifiers differ, it is the same resource. | 662 // If only the fragment identifiers differ, it is the same resource. |
689 DCHECK(EqualIgnoringFragmentIdentifier(resource->Url(), params.Url())); | 663 DCHECK(EqualIgnoringFragmentIdentifier(resource->Url(), params.Url())); |
690 RequestLoadStarted(identifier, resource, params, policy, is_static_data); | 664 RequestLoadStarted(identifier, resource, params, policy, is_static_data); |
691 document_resources_.Set( | 665 document_resources_.Set( |
692 MemoryCache::RemoveFragmentIdentifierIfNeeded(params.Url()), resource); | 666 MemoryCache::RemoveFragmentIdentifierIfNeeded(params.Url()), resource); |
693 | 667 |
694 // Returns with an existing resource if the resource does not need to start | 668 // Returns with an existing resource if the resource does not need to start |
695 // loading immediately. If revalidation policy was determined as |Revalidate|, | 669 // loading immediately. If revalidation policy was determined as |Revalidate|, |
696 // the resource was already initialized for the revalidation here, but won't | 670 // the resource was already initialized for the revalidation here, but won't |
697 // start loading. | 671 // start loading. |
698 if (!ResourceNeedsLoad(resource, params, policy)) { | 672 if (!ResourceNeedsLoad(resource, params, policy)) |
699 if (policy != kUse) | |
700 InsertAsPreloadIfNecessary(resource, params, factory.GetType()); | |
701 return resource; | 673 return resource; |
702 } | |
703 | 674 |
704 if (!StartLoad(resource)) | 675 if (!StartLoad(resource)) |
705 return nullptr; | 676 return nullptr; |
706 | |
707 if (policy != kUse) | |
708 InsertAsPreloadIfNecessary(resource, params, factory.GetType()); | |
709 scoped_resource_load_tracker.ResourceLoadContinuesBeyondScope(); | 677 scoped_resource_load_tracker.ResourceLoadContinuesBeyondScope(); |
710 | 678 |
711 DCHECK(!resource->ErrorOccurred() || | 679 DCHECK(!resource->ErrorOccurred() || |
712 params.Options().synchronous_policy == kRequestSynchronously); | 680 params.Options().synchronous_policy == kRequestSynchronously); |
713 return resource; | 681 return resource; |
714 } | 682 } |
715 | 683 |
716 void ResourceFetcher::ResourceTimingReportTimerFired(TimerBase* timer) { | 684 void ResourceFetcher::ResourceTimingReportTimerFired(TimerBase* timer) { |
717 DCHECK_EQ(timer, &resource_timing_report_timer_); | 685 DCHECK_EQ(timer, &resource_timing_report_timer_); |
718 Vector<RefPtr<ResourceTimingInfo>> timing_reports; | 686 Vector<RefPtr<ResourceTimingInfo>> timing_reports; |
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
852 if (it != resource_timing_info_map_.end()) { | 820 if (it != resource_timing_info_map_.end()) { |
853 it->value->AddRedirect(redirect_response, cross_origin); | 821 it->value->AddRedirect(redirect_response, cross_origin); |
854 } | 822 } |
855 | 823 |
856 if (resource->GetType() == Resource::kMainResource) { | 824 if (resource->GetType() == Resource::kMainResource) { |
857 DCHECK(navigation_timing_info_); | 825 DCHECK(navigation_timing_info_); |
858 navigation_timing_info_->AddRedirect(redirect_response, cross_origin); | 826 navigation_timing_info_->AddRedirect(redirect_response, cross_origin); |
859 } | 827 } |
860 } | 828 } |
861 | 829 |
862 Resource* ResourceFetcher::MatchPreload(const FetchParameters& params, | 830 ResourceFetcher::RevalidationPolicy |
863 Resource::Type type) { | 831 ResourceFetcher::DetermineRevalidationPolicy( |
864 auto it = preloads_.find(PreloadKey(params.Url(), type)); | 832 Resource::Type type, |
865 if (it == preloads_.end()) | 833 const FetchParameters& fetch_params, |
866 return nullptr; | 834 Resource* existing_resource, |
| 835 bool is_static_data) const { |
| 836 const ResourceRequest& request = fetch_params.GetResourceRequest(); |
867 | 837 |
868 Resource* resource = it->value; | 838 if (!existing_resource) |
| 839 return kLoad; |
869 | 840 |
870 RecordSriResourceIntegrityMismatchEvent(kCheckingForIntegrityMismatch); | 841 // If the existing resource is loading and the associated fetcher is not equal |
871 if (resource->MustRefetchDueToIntegrityMetadata(params)) | 842 // to |this|, we must not use the resource. Otherwise, CSP violation may |
872 return nullptr; | 843 // happen in redirect handling. |
873 | 844 if (existing_resource->Loader() && |
874 if (params.IsSpeculativePreload()) | 845 existing_resource->Loader()->Fetcher() != this) { |
875 return resource; | 846 return kReload; |
876 if (params.IsLinkPreload()) { | |
877 resource->SetLinkPreload(true); | |
878 return resource; | |
879 } | 847 } |
880 | 848 |
881 if (!IsReusableForPreloading(params, resource, false)) | 849 // Checks if the resource has an explicit policy about integrity metadata. |
882 return nullptr; | 850 // |
| 851 // This is necessary because ScriptResource and CSSStyleSheetResource objects |
| 852 // do not keep the raw data around after the source is accessed once, so if |
| 853 // the resource is accessed from the MemoryCache for a second time, there is |
| 854 // no way to redo an integrity check. |
| 855 // |
| 856 // Thus, Blink implements a scheme where it caches the integrity information |
| 857 // for those resources after the first time it is checked, and if there is |
| 858 // another request for that resource, with the same integrity metadata, Blink |
| 859 // skips the integrity calculation. However, if the integrity metadata is a |
| 860 // mismatch, the MemoryCache must be skipped here, and a new request for the |
| 861 // resource must be made to get the raw data. This is expected to be an |
| 862 // uncommon case, however, as it implies two same-origin requests to the same |
| 863 // resource, but with different integrity metadata. |
| 864 RecordSriResourceIntegrityMismatchEvent(kCheckingForIntegrityMismatch); |
| 865 if (existing_resource->MustRefetchDueToIntegrityMetadata(fetch_params)) { |
| 866 RecordSriResourceIntegrityMismatchEvent(kRefetchDueToIntegrityMismatch); |
| 867 return kReload; |
| 868 } |
883 | 869 |
884 resource->DecreasePreloadCount(); | 870 // If the same URL has been loaded as a different type, we need to reload. |
885 preloads_.erase(it); | 871 if (existing_resource->GetType() != type) { |
886 return resource; | 872 // FIXME: If existingResource is a Preload and the new type is LinkPrefetch |
887 } | 873 // We really should discard the new prefetch since the preload has more |
| 874 // specific type information! crbug.com/379893 |
| 875 // fast/dom/HTMLLinkElement/link-and-subresource-test hits this case. |
| 876 RESOURCE_LOADING_DVLOG(1) << "ResourceFetcher::determineRevalidationPolicy " |
| 877 "reloading due to type mismatch."; |
| 878 return kReload; |
| 879 } |
888 | 880 |
889 void ResourceFetcher::InsertAsPreloadIfNecessary(Resource* resource, | 881 // We already have a preload going for this URL. |
890 const FetchParameters& params, | 882 if (fetch_params.IsSpeculativePreload() && existing_resource->IsPreloaded()) |
891 Resource::Type type) { | 883 return kUse; |
892 if (!params.IsSpeculativePreload() && !params.IsLinkPreload()) | |
893 return; | |
894 // CSP layout tests verify that preloads are subject to access checks by | |
895 // seeing if they are in the `preload started` list. Therefore do not add | |
896 // them to the list if the load is immediately denied. | |
897 if (resource->GetResourceError().IsAccessCheck()) | |
898 return; | |
899 PreloadKey key(params.Url(), type); | |
900 if (preloads_.find(key) == preloads_.end()) { | |
901 preloads_.insert(key, resource); | |
902 resource->IncreasePreloadCount(); | |
903 if (preloaded_urls_for_test_) | |
904 preloaded_urls_for_test_->insert(resource->Url().GetString()); | |
905 } | |
906 } | |
907 | 884 |
908 bool ResourceFetcher::IsReusableForPreloading(const FetchParameters& params, | |
909 Resource* existing_resource, | |
910 bool is_static_data) const { | |
911 const ResourceRequest& request = params.GetResourceRequest(); | |
912 // Do not load from cache if images are not enabled. There are two general | 885 // Do not load from cache if images are not enabled. There are two general |
913 // cases: | 886 // cases: |
914 // | 887 // |
915 // 1. Images are disabled. Don't ever load images, even if the image is cached | 888 // 1. Images are disabled. Don't ever load images, even if the image is cached |
916 // or it is a data: url. In this case, we "Reload" the image, then defer it | 889 // or it is a data: url. In this case, we "Reload" the image, then defer it |
917 // with resourceNeedsLoad() so that it never actually goes to the network. | 890 // with resourceNeedsLoad() so that it never actually goes to the network. |
918 // | 891 // |
919 // 2. Images are enabled, but not loaded automatically. In this case, we will | 892 // 2. Images are enabled, but not loaded automatically. In this case, we will |
920 // Use cached resources or data: urls, but will similarly fall back to a | 893 // Use cached resources or data: urls, but will similarly fall back to a |
921 // deferred network load if we don't have the data available without a network | 894 // deferred network load if we don't have the data available without a network |
922 // request. We check allowImage() here, which is affected by m_imagesEnabled | 895 // request. We check allowImage() here, which is affected by m_imagesEnabled |
923 // but not m_autoLoadImages, in order to allow for this differing behavior. | 896 // but not m_autoLoadImages, in order to allow for this differing behavior. |
924 // | 897 // |
925 // TODO(japhet): Can we get rid of one of these settings? | 898 // TODO(japhet): Can we get rid of one of these settings? |
926 if (existing_resource->IsImage() && | 899 if (existing_resource->IsImage() && |
927 !Context().AllowImage(images_enabled_, existing_resource->Url())) { | 900 !Context().AllowImage(images_enabled_, existing_resource->Url())) { |
928 return false; | 901 return kReload; |
929 } | 902 } |
930 | 903 |
931 // Never use cache entries for downloadToFile / useStreamOnResponse requests. | 904 // Never use cache entries for downloadToFile / useStreamOnResponse requests. |
932 // The data will be delivered through other paths. | 905 // The data will be delivered through other paths. |
933 if (request.DownloadToFile() || request.UseStreamOnResponse()) | 906 if (request.DownloadToFile() || request.UseStreamOnResponse()) |
934 return false; | 907 return kReload; |
935 | 908 |
936 // Never reuse opaque responses from a service worker for requests that are | 909 // Never reuse opaque responses from a service worker for requests that are |
937 // not no-cors. https://crbug.com/625575 | 910 // not no-cors. https://crbug.com/625575 |
938 if (existing_resource->GetResponse().WasFetchedViaServiceWorker() && | 911 if (existing_resource->GetResponse().WasFetchedViaServiceWorker() && |
939 existing_resource->GetResponse().ServiceWorkerResponseType() == | 912 existing_resource->GetResponse().ServiceWorkerResponseType() == |
940 kWebServiceWorkerResponseTypeOpaque && | 913 kWebServiceWorkerResponseTypeOpaque && |
941 request.GetFetchRequestMode() != WebURLRequest::kFetchRequestModeNoCORS) { | 914 request.GetFetchRequestMode() != WebURLRequest::kFetchRequestModeNoCORS) { |
942 return false; | 915 return kReload; |
943 } | 916 } |
944 | 917 |
945 if (!is_static_data && !existing_resource->CanReuse(params)) | 918 if (!is_static_data && !existing_resource->CanReuse(fetch_params)) |
946 return false; | 919 return kReload; |
947 | 920 |
948 // Certain requests (e.g., XHRs) might have manually set headers that require | 921 // Certain requests (e.g., XHRs) might have manually set headers that require |
949 // revalidation. In theory, this should be a Revalidate case. In practice, the | 922 // revalidation. In theory, this should be a Revalidate case. In practice, the |
950 // MemoryCache revalidation path assumes a whole bunch of things about how | 923 // MemoryCache revalidation path assumes a whole bunch of things about how |
951 // revalidation works that manual headers violate, so punt to Reload instead. | 924 // revalidation works that manual headers violate, so punt to Reload instead. |
952 // | 925 // |
953 // Similarly, a request with manually added revalidation headers can lead to a | 926 // Similarly, a request with manually added revalidation headers can lead to a |
954 // 304 response for a request that wasn't flagged as a revalidation attempt. | 927 // 304 response for a request that wasn't flagged as a revalidation attempt. |
955 // Normally, successful revalidation will maintain the original response's | 928 // Normally, successful revalidation will maintain the original response's |
956 // status code, but for a manual revalidation the response code remains 304. | 929 // status code, but for a manual revalidation the response code remains 304. |
957 // In this case, the Resource likely has insufficient context to provide a | 930 // In this case, the Resource likely has insufficient context to provide a |
958 // useful cache hit or revalidation. See http://crbug.com/643659 | 931 // useful cache hit or revalidation. See http://crbug.com/643659 |
959 if (!is_static_data && | 932 if (!is_static_data && |
960 (request.IsConditional() || | 933 (request.IsConditional() || |
961 existing_resource->GetResponse().HttpStatusCode() == 304)) { | 934 existing_resource->GetResponse().HttpStatusCode() == 304)) { |
962 return false; | 935 return kReload; |
963 } | 936 } |
964 | 937 |
965 if (!is_static_data && | 938 if (!is_static_data && |
966 !params.Options().CanReuseRequest(existing_resource->Options())) { | 939 !fetch_params.Options().CanReuseRequest(existing_resource->Options())) { |
967 return false; | |
968 } | |
969 | |
970 return true; | |
971 } | |
972 | |
973 ResourceFetcher::RevalidationPolicy | |
974 ResourceFetcher::DetermineRevalidationPolicy( | |
975 Resource::Type type, | |
976 const FetchParameters& fetch_params, | |
977 Resource* existing_resource, | |
978 bool is_static_data) const { | |
979 const ResourceRequest& request = fetch_params.GetResourceRequest(); | |
980 | |
981 if (!existing_resource) | |
982 return kLoad; | |
983 | |
984 // If the existing resource is loading and the associated fetcher is not equal | |
985 // to |this|, we must not use the resource. Otherwise, CSP violation may | |
986 // happen in redirect handling. | |
987 if (existing_resource->Loader() && | |
988 existing_resource->Loader()->Fetcher() != this) { | |
989 return kReload; | 940 return kReload; |
990 } | 941 } |
991 | 942 |
992 // Checks if the resource has an explicit policy about integrity metadata. | 943 // Always use preloads. |
993 // | 944 if (existing_resource->IsPreloaded()) |
994 // This is necessary because ScriptResource and CSSStyleSheetResource objects | 945 return kUse; |
995 // do not keep the raw data around after the source is accessed once, so if | |
996 // the resource is accessed from the MemoryCache for a second time, there is | |
997 // no way to redo an integrity check. | |
998 // | |
999 // Thus, Blink implements a scheme where it caches the integrity information | |
1000 // for those resources after the first time it is checked, and if there is | |
1001 // another request for that resource, with the same integrity metadata, Blink | |
1002 // skips the integrity calculation. However, if the integrity metadata is a | |
1003 // mismatch, the MemoryCache must be skipped here, and a new request for the | |
1004 // resource must be made to get the raw data. This is expected to be an | |
1005 // uncommon case, however, as it implies two same-origin requests to the same | |
1006 // resource, but with different integrity metadata. | |
1007 RecordSriResourceIntegrityMismatchEvent(kCheckingForIntegrityMismatch); | |
1008 if (existing_resource->MustRefetchDueToIntegrityMetadata(fetch_params)) { | |
1009 RecordSriResourceIntegrityMismatchEvent(kRefetchDueToIntegrityMismatch); | |
1010 return kReload; | |
1011 } | |
1012 | |
1013 // If the same URL has been loaded as a different type, we need to reload. | |
1014 if (existing_resource->GetType() != type) { | |
1015 // FIXME: If existingResource is a Preload and the new type is LinkPrefetch | |
1016 // We really should discard the new prefetch since the preload has more | |
1017 // specific type information! crbug.com/379893 | |
1018 // fast/dom/HTMLLinkElement/link-and-subresource-test hits this case. | |
1019 RESOURCE_LOADING_DVLOG(1) << "ResourceFetcher::determineRevalidationPolicy " | |
1020 "reloading due to type mismatch."; | |
1021 return kReload; | |
1022 } | |
1023 | |
1024 // If |existing_resource| is not reusable as a preloaded resource, it should | |
1025 // not be reusable as a normal resource as well. | |
1026 if (!IsReusableForPreloading(fetch_params, existing_resource, is_static_data)) | |
1027 return kReload; | |
1028 | 946 |
1029 // If resource was populated from a SubstituteData load or data: url, use it. | 947 // If resource was populated from a SubstituteData load or data: url, use it. |
1030 if (is_static_data) | 948 if (is_static_data) |
1031 return kUse; | 949 return kUse; |
1032 | 950 |
1033 // Don't reload resources while pasting. | 951 // Don't reload resources while pasting. |
1034 if (allow_stale_resources_) | 952 if (allow_stale_resources_) |
1035 return kUse; | 953 return kUse; |
1036 | 954 |
1037 // WebCachePolicy::ReturnCacheDataElseLoad uses the cache no matter what. | 955 // WebCachePolicy::ReturnCacheDataElseLoad uses the cache no matter what. |
(...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1178 } | 1096 } |
1179 | 1097 |
1180 int ResourceFetcher::BlockingRequestCount() const { | 1098 int ResourceFetcher::BlockingRequestCount() const { |
1181 return loaders_.size(); | 1099 return loaders_.size(); |
1182 } | 1100 } |
1183 | 1101 |
1184 int ResourceFetcher::NonblockingRequestCount() const { | 1102 int ResourceFetcher::NonblockingRequestCount() const { |
1185 return non_blocking_loaders_.size(); | 1103 return non_blocking_loaders_.size(); |
1186 } | 1104 } |
1187 | 1105 |
| 1106 void ResourceFetcher::PreloadStarted(Resource* resource) { |
| 1107 if (preloads_.Contains(resource)) |
| 1108 return; |
| 1109 resource->IncreasePreloadCount(); |
| 1110 |
| 1111 preloads_.insert(resource); |
| 1112 |
| 1113 if (preloaded_urls_for_test_) |
| 1114 preloaded_urls_for_test_->insert(resource->Url().GetString()); |
| 1115 } |
| 1116 |
1188 void ResourceFetcher::EnableIsPreloadedForTest() { | 1117 void ResourceFetcher::EnableIsPreloadedForTest() { |
1189 if (preloaded_urls_for_test_) | 1118 if (preloaded_urls_for_test_) |
1190 return; | 1119 return; |
1191 preloaded_urls_for_test_ = WTF::WrapUnique(new HashSet<String>); | 1120 preloaded_urls_for_test_ = WTF::WrapUnique(new HashSet<String>); |
1192 | 1121 |
1193 for (const auto& pair : preloads_) { | 1122 for (const auto& resource : preloads_) |
1194 Resource* resource = pair.value; | |
1195 preloaded_urls_for_test_->insert(resource->Url().GetString()); | 1123 preloaded_urls_for_test_->insert(resource->Url().GetString()); |
1196 } | |
1197 } | 1124 } |
1198 | 1125 |
1199 bool ResourceFetcher::IsPreloadedForTest(const KURL& url) const { | 1126 bool ResourceFetcher::IsPreloadedForTest(const KURL& url) const { |
1200 DCHECK(preloaded_urls_for_test_); | 1127 DCHECK(preloaded_urls_for_test_); |
1201 return preloaded_urls_for_test_->Contains(url.GetString()); | 1128 return preloaded_urls_for_test_->Contains(url.GetString()); |
1202 } | 1129 } |
1203 | 1130 |
1204 void ResourceFetcher::ClearPreloads(ClearPreloadsPolicy policy) { | 1131 void ResourceFetcher::ClearPreloads(ClearPreloadsPolicy policy) { |
1205 LogPreloadStats(policy); | 1132 LogPreloadStats(policy); |
1206 | 1133 |
1207 Vector<PreloadKey> keys_to_be_removed; | 1134 for (const auto& resource : preloads_) { |
1208 for (const auto& pair : preloads_) { | |
1209 Resource* resource = pair.value; | |
1210 if (policy == kClearAllPreloads || !resource->IsLinkPreload()) { | 1135 if (policy == kClearAllPreloads || !resource->IsLinkPreload()) { |
1211 resource->DecreasePreloadCount(); | 1136 resource->DecreasePreloadCount(); |
1212 if (resource->GetPreloadResult() == Resource::kPreloadNotReferenced) | 1137 if (resource->GetPreloadResult() == Resource::kPreloadNotReferenced) |
1213 GetMemoryCache()->Remove(resource); | 1138 GetMemoryCache()->Remove(resource.Get()); |
1214 keys_to_be_removed.push_back(pair.key); | 1139 preloads_.erase(resource); |
1215 } | 1140 } |
1216 } | 1141 } |
1217 preloads_.RemoveAll(keys_to_be_removed); | |
1218 } | 1142 } |
1219 | 1143 |
1220 void ResourceFetcher::WarnUnusedPreloads() { | 1144 void ResourceFetcher::WarnUnusedPreloads() { |
1221 for (const auto& pair : preloads_) { | 1145 for (const auto& resource : preloads_) { |
1222 Resource* resource = pair.value; | |
1223 if (resource && resource->IsLinkPreload() && | 1146 if (resource && resource->IsLinkPreload() && |
1224 resource->GetPreloadResult() == Resource::kPreloadNotReferenced) { | 1147 resource->GetPreloadResult() == Resource::kPreloadNotReferenced) { |
1225 Context().AddConsoleMessage( | 1148 Context().AddConsoleMessage( |
1226 "The resource " + resource->Url().GetString() + | 1149 "The resource " + resource->Url().GetString() + |
1227 " was preloaded using link preload but not used within a few " | 1150 " was preloaded using link preload but not used within a few " |
1228 "seconds from the window's load event. Please make sure it " | 1151 "seconds from the window's load event. Please make sure it " |
1229 "wasn't preloaded for nothing.", | 1152 "wasn't preloaded for nothing.", |
1230 FetchContext::kLogWarningMessage); | 1153 FetchContext::kLogWarningMessage); |
1231 } | 1154 } |
1232 } | 1155 } |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1319 | 1242 |
1320 resource_timing_info_map_.Take(resource); | 1243 resource_timing_info_map_.Take(resource); |
1321 | 1244 |
1322 bool is_internal_request = resource->Options().initiator_info.name == | 1245 bool is_internal_request = resource->Options().initiator_info.name == |
1323 FetchInitiatorTypeNames::internal; | 1246 FetchInitiatorTypeNames::internal; |
1324 | 1247 |
1325 Context().DispatchDidFail(resource->Identifier(), error, | 1248 Context().DispatchDidFail(resource->Identifier(), error, |
1326 resource->GetResponse().EncodedDataLength(), | 1249 resource->GetResponse().EncodedDataLength(), |
1327 is_internal_request); | 1250 is_internal_request); |
1328 | 1251 |
1329 if (error.IsCancellation()) | |
1330 RemovePreload(resource); | |
1331 resource->FinishAsError(error); | 1252 resource->FinishAsError(error); |
1332 | 1253 |
1333 HandleLoadCompletion(resource); | 1254 HandleLoadCompletion(resource); |
1334 } | 1255 } |
1335 | 1256 |
1336 void ResourceFetcher::MoveResourceLoaderToNonBlocking(ResourceLoader* loader) { | 1257 void ResourceFetcher::MoveResourceLoaderToNonBlocking(ResourceLoader* loader) { |
1337 DCHECK(loader); | 1258 DCHECK(loader); |
1338 // TODO(yoav): Convert CHECK to DCHECK if no crash reports come in. | 1259 // TODO(yoav): Convert CHECK to DCHECK if no crash reports come in. |
1339 CHECK(loaders_.Contains(loader)); | 1260 CHECK(loaders_.Contains(loader)); |
1340 non_blocking_loaders_.insert(loader); | 1261 non_blocking_loaders_.insert(loader); |
(...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1479 unsigned fonts = 0; | 1400 unsigned fonts = 0; |
1480 unsigned font_misses = 0; | 1401 unsigned font_misses = 0; |
1481 unsigned medias = 0; | 1402 unsigned medias = 0; |
1482 unsigned media_misses = 0; | 1403 unsigned media_misses = 0; |
1483 unsigned text_tracks = 0; | 1404 unsigned text_tracks = 0; |
1484 unsigned text_track_misses = 0; | 1405 unsigned text_track_misses = 0; |
1485 unsigned imports = 0; | 1406 unsigned imports = 0; |
1486 unsigned import_misses = 0; | 1407 unsigned import_misses = 0; |
1487 unsigned raws = 0; | 1408 unsigned raws = 0; |
1488 unsigned raw_misses = 0; | 1409 unsigned raw_misses = 0; |
1489 for (const auto& pair : preloads_) { | 1410 for (const auto& resource : preloads_) { |
1490 Resource* resource = pair.value; | |
1491 // Do not double count link rel preloads. These do not get cleared if the | 1411 // Do not double count link rel preloads. These do not get cleared if the |
1492 // ClearPreloadsPolicy is only clearing speculative markup preloads. | 1412 // ClearPreloadsPolicy is only clearing speculative markup preloads. |
1493 if (resource->IsLinkPreload() && | 1413 if (resource->IsLinkPreload() && |
1494 policy == kClearSpeculativeMarkupPreloads) { | 1414 policy == kClearSpeculativeMarkupPreloads) { |
1495 continue; | 1415 continue; |
1496 } | 1416 } |
1497 int miss_count = | 1417 int miss_count = |
1498 resource->GetPreloadResult() == Resource::kPreloadNotReferenced ? 1 : 0; | 1418 resource->GetPreloadResult() == Resource::kPreloadNotReferenced ? 1 : 0; |
1499 switch (resource->GetType()) { | 1419 switch (resource->GetType()) { |
1500 case Resource::kImage: | 1420 case Resource::kImage: |
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1638 visitor->Trace(context_); | 1558 visitor->Trace(context_); |
1639 visitor->Trace(archive_); | 1559 visitor->Trace(archive_); |
1640 visitor->Trace(loaders_); | 1560 visitor->Trace(loaders_); |
1641 visitor->Trace(non_blocking_loaders_); | 1561 visitor->Trace(non_blocking_loaders_); |
1642 visitor->Trace(document_resources_); | 1562 visitor->Trace(document_resources_); |
1643 visitor->Trace(preloads_); | 1563 visitor->Trace(preloads_); |
1644 visitor->Trace(resource_timing_info_map_); | 1564 visitor->Trace(resource_timing_info_map_); |
1645 } | 1565 } |
1646 | 1566 |
1647 } // namespace blink | 1567 } // namespace blink |
OLD | NEW |