146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// Copyright 2014 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_service_impl.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <functional> 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind.h" 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind_helpers.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/logging.h" 12ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch#include "base/message_loop/message_loop.h" 1303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)#include "base/single_thread_task_runner.h" 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/stl_util.h" 15116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache.h" 16116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_backend_impl.h" 17116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_entry.h" 18116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_executable_handler.h" 19116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_histograms.h" 20116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_policy.h" 21116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_quota_client.h" 22116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_response.h" 23116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_service_impl.h" 24116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/browser/appcache/appcache_storage_impl.h" 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/completion_callback.h" 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/io_buffer.h" 271320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "storage/browser/quota/special_storage_policy.h" 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 29116680a4aac90f2aa7413d9095a592090648e557Ben Murdochnamespace content { 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DeferredCallback(const net::CompletionCallback& callback, int rv) { 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback.Run(rv); 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)AppCacheInfoCollection::AppCacheInfoCollection() {} 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)AppCacheInfoCollection::~AppCacheInfoCollection() {} 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// AsyncHelper ------- 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)class AppCacheServiceImpl::AsyncHelper 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : public AppCacheStorage::Delegate { 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 4846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AsyncHelper(AppCacheServiceImpl* service, 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : service_(service), callback_(callback) { 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->pending_helpers_.insert(this); 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~AsyncHelper() { 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (service_) 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->pending_helpers_.erase(this); 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void Start() = 0; 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void Cancel(); 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void CallCallback(int rv) { 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!callback_.is_null()) { 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Defer to guarantee async completion. 66b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) base::MessageLoop::current()->PostTask( 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FROM_HERE, base::Bind(&DeferredCallback, callback_, rv)); 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback_.Reset(); 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AppCacheServiceImpl* service_; 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::CompletionCallback callback_; 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::AsyncHelper::Cancel() { 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!callback_.is_null()) { 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback_.Run(net::ERR_ABORTED); 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback_.Reset(); 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->CancelDelegateCallbacks(this); 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_ = NULL; 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// CanHandleOfflineHelper ------- 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)class AppCacheServiceImpl::CanHandleOfflineHelper : AsyncHelper { 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CanHandleOfflineHelper( 9046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AppCacheServiceImpl* service, const GURL& url, 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& first_party, const net::CompletionCallback& callback) 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : AsyncHelper(service, callback), 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) url_(url), 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) first_party_(first_party) { 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void Start() OVERRIDE { 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCachePolicy* policy = service_->appcache_policy(); 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (policy && !policy->CanLoadAppCache(url_, first_party_)) { 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(net::ERR_FAILED); 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->FindResponseForMainRequest(url_, GURL(), this); 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // AppCacheStorage::Delegate implementation. 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnMainResponseFound( 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& url, const AppCacheEntry& entry, 1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& fallback_url, const AppCacheEntry& fallback_entry, 1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 cache_id, int64 group_id, const GURL& mainfest_url) OVERRIDE; 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GURL url_; 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GURL first_party_; 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(CanHandleOfflineHelper); 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 12146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::CanHandleOfflineHelper::OnMainResponseFound( 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& url, const AppCacheEntry& entry, 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& fallback_url, const AppCacheEntry& fallback_entry, 1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 cache_id, int64 group_id, const GURL& manifest_url) { 1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool can = (entry.has_response_id() || fallback_entry.has_response_id()); 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(can ? net::OK : net::ERR_FAILED); 1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// DeleteHelper ------- 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)class AppCacheServiceImpl::DeleteHelper : public AsyncHelper { 1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DeleteHelper( 13546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AppCacheServiceImpl* service, const GURL& manifest_url, 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : AsyncHelper(service, callback), manifest_url_(manifest_url) { 1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void Start() OVERRIDE { 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->LoadOrCreateGroup(manifest_url_, this); 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // AppCacheStorage::Delegate implementation. 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnGroupLoaded( 147116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch AppCacheGroup* group, const GURL& manifest_url) OVERRIDE; 148116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch virtual void OnGroupMadeObsolete(AppCacheGroup* group, 149e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch bool success, 150e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch int response_code) OVERRIDE; 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GURL manifest_url_; 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(DeleteHelper); 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 15646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteHelper::OnGroupLoaded( 157116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch AppCacheGroup* group, const GURL& manifest_url) { 1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (group) { 1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) group->set_being_deleted(true); 1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) group->CancelUpdate(); 161e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch service_->storage()->MakeGroupObsolete(group, this, 0); 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(net::ERR_FAILED); 1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 16846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteHelper::OnGroupMadeObsolete( 169116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch AppCacheGroup* group, 170e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch bool success, 171e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch int response_code) { 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(success ? net::OK : net::ERR_FAILED); 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// DeleteOriginHelper ------- 1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 17846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)class AppCacheServiceImpl::DeleteOriginHelper : public AsyncHelper { 1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DeleteOriginHelper( 18146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AppCacheServiceImpl* service, const GURL& origin, 1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) 1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : AsyncHelper(service, callback), origin_(origin), 1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) num_caches_to_delete_(0), successes_(0), failures_(0) { 1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void Start() OVERRIDE { 1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We start by listing all caches, continues in OnAllInfo(). 1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->GetAllInfo(this); 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // AppCacheStorage::Delegate implementation. 1942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnAllInfo(AppCacheInfoCollection* collection) OVERRIDE; 1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnGroupLoaded( 196116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch AppCacheGroup* group, const GURL& manifest_url) OVERRIDE; 197116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch virtual void OnGroupMadeObsolete(AppCacheGroup* group, 198e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch bool success, 199e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch int response_code) OVERRIDE; 2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void CacheCompleted(bool success); 2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GURL origin_; 2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int num_caches_to_delete_; 2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int successes_; 2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int failures_; 2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(DeleteOriginHelper); 2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 21146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteOriginHelper::OnAllInfo( 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheInfoCollection* collection) { 2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!collection) { 2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Failed to get a listing. 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(net::ERR_FAILED); 2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::map<GURL, AppCacheInfoVector>::iterator found = 2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) collection->infos_by_origin.find(origin_); 2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (found == collection->infos_by_origin.end() || found->second.empty()) { 2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // No caches for this origin. 2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(net::OK); 2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We have some caches to delete. 2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const AppCacheInfoVector& caches_to_delete = found->second; 2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) successes_ = 0; 2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) failures_ = 0; 2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) num_caches_to_delete_ = static_cast<int>(caches_to_delete.size()); 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (AppCacheInfoVector::const_iterator iter = caches_to_delete.begin(); 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) iter != caches_to_delete.end(); ++iter) { 2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->LoadOrCreateGroup(iter->manifest_url, this); 2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 24046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteOriginHelper::OnGroupLoaded( 241116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch AppCacheGroup* group, const GURL& manifest_url) { 2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (group) { 2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) group->set_being_deleted(true); 2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) group->CancelUpdate(); 245e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch service_->storage()->MakeGroupObsolete(group, this, 0); 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CacheCompleted(false); 2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 25146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteOriginHelper::OnGroupMadeObsolete( 252116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch AppCacheGroup* group, 253e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch bool success, 254e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch int response_code) { 2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CacheCompleted(success); 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 25846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteOriginHelper::CacheCompleted(bool success) { 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (success) 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++successes_; 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++failures_; 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if ((successes_ + failures_) < num_caches_to_delete_) 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(!failures_ ? net::OK : net::ERR_FAILED); 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// GetInfoHelper ------- 2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 27346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)class AppCacheServiceImpl::GetInfoHelper : AsyncHelper { 2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetInfoHelper( 27646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AppCacheServiceImpl* service, AppCacheInfoCollection* collection, 2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : AsyncHelper(service, callback), collection_(collection) { 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void Start() OVERRIDE { 2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->GetAllInfo(this); 2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // AppCacheStorage::Delegate implementation. 2872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnAllInfo(AppCacheInfoCollection* collection) OVERRIDE; 2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_refptr<AppCacheInfoCollection> collection_; 2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(GetInfoHelper); 2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 29446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::GetInfoHelper::OnAllInfo( 2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheInfoCollection* collection) { 2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (collection) 2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) collection->infos_by_origin.swap(collection_->infos_by_origin); 2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CallCallback(collection ? net::OK : net::ERR_FAILED); 2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// CheckResponseHelper ------- 3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 30446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)class AppCacheServiceImpl::CheckResponseHelper : AsyncHelper { 3055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CheckResponseHelper( 30746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) AppCacheServiceImpl* service, const GURL& manifest_url, int64 cache_id, 3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 response_id) 3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : AsyncHelper(service, net::CompletionCallback()), 3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) manifest_url_(manifest_url), 3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) cache_id_(cache_id), 3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) response_id_(response_id), 3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) kIOBufferSize(32 * 1024), 3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) expected_total_size_(0), 3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) amount_headers_read_(0), 3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) amount_data_read_(0) { 3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void Start() OVERRIDE { 3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->storage()->LoadOrCreateGroup(manifest_url_, this); 3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void Cancel() OVERRIDE { 3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CountCheckResponseResult( 3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CHECK_CANCELED); 3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) response_reader_.reset(); 3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AsyncHelper::Cancel(); 3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 3312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnGroupLoaded(AppCacheGroup* group, 3322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const GURL& manifest_url) OVERRIDE; 3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void OnReadInfoComplete(int result); 3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void OnReadDataComplete(int result); 3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Inputs describing what to check. 3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GURL manifest_url_; 3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 cache_id_; 3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 response_id_; 3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Internals used to perform the checks. 3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const int kIOBufferSize; 3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_refptr<AppCache> cache_; 3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<AppCacheResponseReader> response_reader_; 3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_refptr<HttpResponseInfoIOBuffer> info_buffer_; 3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_refptr<net::IOBuffer> data_buffer_; 3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 expected_total_size_; 3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int amount_headers_read_; 3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int amount_data_read_; 3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(CheckResponseHelper); 3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 35346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::CheckResponseHelper::OnGroupLoaded( 3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheGroup* group, const GURL& manifest_url) { 3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK_EQ(manifest_url_, manifest_url); 3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!group || !group->newest_complete_cache() || group->is_being_deleted() || 3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) group->is_obsolete()) { 3585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CountCheckResponseResult( 3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::MANIFEST_OUT_OF_DATE); 3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) cache_ = group->newest_complete_cache(); 3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const AppCacheEntry* entry = cache_->GetEntryWithResponseId(response_id_); 3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!entry) { 3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (cache_->cache_id() == cache_id_) { 3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CountCheckResponseResult( 3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::ENTRY_NOT_FOUND); 3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->DeleteAppCacheGroup(manifest_url_, net::CompletionCallback()); 3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CountCheckResponseResult( 3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::RESPONSE_OUT_OF_DATE); 3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Verify that we can read the response info and data. 3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) expected_total_size_ = entry->response_size(); 3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) response_reader_.reset(service_->storage()->CreateResponseReader( 3825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) manifest_url_, group->group_id(), response_id_)); 3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) info_buffer_ = new HttpResponseInfoIOBuffer(); 3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) response_reader_->ReadInfo( 385868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) info_buffer_.get(), 386868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Bind(&CheckResponseHelper::OnReadInfoComplete, 387868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Unretained(this))); 3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 39046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::CheckResponseHelper::OnReadInfoComplete(int result) { 3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (result < 0) { 3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CountCheckResponseResult( 3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::READ_HEADERS_ERROR); 3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->DeleteAppCacheGroup(manifest_url_, net::CompletionCallback()); 3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) amount_headers_read_ = result; 3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Start reading the data. 4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) data_buffer_ = new net::IOBuffer(kIOBufferSize); 4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) response_reader_->ReadData( 403868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) data_buffer_.get(), 404868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) kIOBufferSize, 4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind(&CheckResponseHelper::OnReadDataComplete, 4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Unretained(this))); 4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 40946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::CheckResponseHelper::OnReadDataComplete(int result) { 4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (result > 0) { 4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Keep reading until we've read thru everything or failed to read. 4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) amount_data_read_ += result; 4135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) response_reader_->ReadData( 414868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) data_buffer_.get(), 415868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) kIOBufferSize, 4165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind(&CheckResponseHelper::OnReadDataComplete, 4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Unretained(this))); 4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 4195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CheckResponseResultType check_result; 4225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (result < 0) 4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) check_result = AppCacheHistograms::READ_DATA_ERROR; 4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else if (info_buffer_->response_data_size != amount_data_read_ || 4255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) expected_total_size_ != amount_data_read_ + amount_headers_read_) 4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) check_result = AppCacheHistograms::UNEXPECTED_DATA_SIZE; 4275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else 4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) check_result = AppCacheHistograms::RESPONSE_OK; 4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheHistograms::CountCheckResponseResult(check_result); 4305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (check_result != AppCacheHistograms::RESPONSE_OK) 4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) service_->DeleteAppCacheGroup(manifest_url_, net::CompletionCallback()); 4335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delete this; 4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4361e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)// AppCacheStorageReference ------ 4371e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 4381e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)AppCacheStorageReference::AppCacheStorageReference( 4391e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) scoped_ptr<AppCacheStorage> storage) 4401e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) : storage_(storage.Pass()) {} 4411e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)AppCacheStorageReference::~AppCacheStorageReference() {} 4421e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 44346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// AppCacheServiceImpl ------- 4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 44503b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)AppCacheServiceImpl::AppCacheServiceImpl( 44603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) storage::QuotaManagerProxy* quota_manager_proxy) 44703b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) : appcache_policy_(NULL), 44803b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) quota_client_(NULL), 44903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) handler_factory_(NULL), 4505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) quota_manager_proxy_(quota_manager_proxy), 4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) request_context_(NULL), 4525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) force_keep_session_state_(false) { 453868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (quota_manager_proxy_.get()) { 4545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) quota_client_ = new AppCacheQuotaClient(this); 4555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) quota_manager_proxy_->RegisterClient(quota_client_); 4565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 45946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)AppCacheServiceImpl::~AppCacheServiceImpl() { 4605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(backends_.empty()); 4615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::for_each(pending_helpers_.begin(), 4625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pending_helpers_.end(), 4635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::mem_fun(&AsyncHelper::Cancel)); 4645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) STLDeleteElements(&pending_helpers_); 4655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (quota_client_) 4665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) quota_client_->NotifyAppCacheDestroyed(); 4675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Destroy storage_ first; ~AppCacheStorageImpl accesses other data members 4695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // (special_storage_policy_). 4705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) storage_.reset(); 4715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 47303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)void AppCacheServiceImpl::Initialize( 47403b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) const base::FilePath& cache_directory, 47503b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) const scoped_refptr<base::SingleThreadTaskRunner>& db_thread, 47603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) const scoped_refptr<base::SingleThreadTaskRunner>& cache_thread) { 4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(!storage_.get()); 4781e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) cache_directory_ = cache_directory; 4791e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) db_thread_ = db_thread; 4801e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) cache_thread_ = cache_thread; 4815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheStorageImpl* storage = new AppCacheStorageImpl(this); 4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) storage->Initialize(cache_directory, db_thread, cache_thread); 4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) storage_.reset(storage); 4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 48646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::ScheduleReinitialize() { 4875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (reinit_timer_.IsRunning()) 4881e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) return; 4895d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 4905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Reinitialization only happens when corruption has been noticed. 4915d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // We don't want to thrash the disk but we also don't want to 4925d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // leave the appcache disabled for an indefinite period of time. Some 4935d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // users never shutdown the browser. 4945d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 4955d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const base::TimeDelta kZeroDelta; 4965d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const base::TimeDelta kOneHour(base::TimeDelta::FromHours(1)); 4975d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const base::TimeDelta k30Seconds(base::TimeDelta::FromSeconds(30)); 4985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 4995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // If the system managed to stay up for long enough, reset the 5005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // delay so a new failure won't incur a long wait to get going again. 5015d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) base::TimeDelta up_time = base::Time::Now() - last_reinit_time_; 5025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (next_reinit_delay_ != kZeroDelta && up_time > kOneHour) 5035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) next_reinit_delay_ = kZeroDelta; 5045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 5055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) reinit_timer_.Start(FROM_HERE, next_reinit_delay_, 50646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) this, &AppCacheServiceImpl::Reinitialize); 5075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 5085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Adjust the delay for next time. 5095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) base::TimeDelta increment = std::max(k30Seconds, next_reinit_delay_); 5105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) next_reinit_delay_ = std::min(next_reinit_delay_ + increment, kOneHour); 5115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 5125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 51346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::Reinitialize() { 5145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) AppCacheHistograms::CountReinitAttempt(!last_reinit_time_.is_null()); 5155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) last_reinit_time_ = base::Time::Now(); 5161e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 5171e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) // Inform observers of about this and give them a chance to 5181e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) // defer deletion of the old storage object. 5191e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) scoped_refptr<AppCacheStorageReference> 5201e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) old_storage_ref(new AppCacheStorageReference(storage_.Pass())); 5211e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) FOR_EACH_OBSERVER(Observer, observers_, 5221e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) OnServiceReinitialized(old_storage_ref.get())); 5231e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 5241e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) Initialize(cache_directory_, db_thread_, cache_thread_); 5251e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)} 5261e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 52746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::CanHandleMainResourceOffline( 5285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& url, 5295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& first_party, 5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) { 5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CanHandleOfflineHelper* helper = 5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) new CanHandleOfflineHelper(this, url, first_party, callback); 5335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) helper->Start(); 5345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 53646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::GetAllAppCacheInfo( 5375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheInfoCollection* collection, 5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) { 5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(collection); 5405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetInfoHelper* helper = new GetInfoHelper(this, collection, callback); 5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) helper->Start(); 5425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 54446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteAppCacheGroup( 5455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& manifest_url, 5465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const net::CompletionCallback& callback) { 5475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DeleteHelper* helper = new DeleteHelper(this, manifest_url, callback); 5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) helper->Start(); 5495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::DeleteAppCachesForOrigin( 5525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const GURL& origin, const net::CompletionCallback& callback) { 5535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DeleteOriginHelper* helper = new DeleteOriginHelper(this, origin, callback); 5545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) helper->Start(); 5555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::CheckAppCacheResponse(const GURL& manifest_url, 5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 cache_id, 5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int64 response_id) { 5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CheckResponseHelper* helper = new CheckResponseHelper( 5615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this, manifest_url, cache_id, response_id); 5625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) helper->Start(); 5635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 56546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::set_special_storage_policy( 56603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) storage::SpecialStoragePolicy* policy) { 5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) special_storage_policy_ = policy; 5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 57046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::RegisterBackend( 5715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheBackendImpl* backend_impl) { 5725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(backends_.find(backend_impl->process_id()) == backends_.end()); 5735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) backends_.insert( 5745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BackendMap::value_type(backend_impl->process_id(), backend_impl)); 5755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 57746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)void AppCacheServiceImpl::UnregisterBackend( 5785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AppCacheBackendImpl* backend_impl) { 5795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) backends_.erase(backend_impl->process_id()); 5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 582116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} // namespace content 583