Backout bug 674728 part 3 due to missing reviews.

This commit is contained in:
Ryan VanderMeulen 2012-03-31 18:18:08 -04:00
Родитель f149464511
Коммит d72a2f5230
5 изменённых файлов: 89 добавлений и 338 удалений

Просмотреть файл

@ -97,23 +97,6 @@ interface nsIApplicationCacheNamespace : nsISupports
readonly attribute ACString data;
};
/**
* Callback for asynchronized methods for nsIApplicationCache.
*/
[scriptable, uuid(062c8061-7c31-44a4-bd8d-302772e4a7eb)]
interface nsIApplicationCacheAsyncCallback : nsISupports
{
const long APP_CACHE_REQUEST_SUCCESS = 0;
const long APP_CACHE_REQUEST_ERROR = 1;
/**
* Callback function with result code. It should be a nsresult.
*
* @param aState is an error code, one of APP_CACHE_REQUEST_*.
*/
void handleAsyncCompletion(in PRUint32 aState);
};
/**
* Application caches store resources for offline use. Each
* application cache has a unique client ID for use with
@ -204,11 +187,6 @@ interface nsIApplicationCache : nsISupports
*/
void discard();
/**
* Discard this application cache in asynchronized.
*/
void discardAsync([optional] in nsIApplicationCacheAsyncCallback aCallback);
/**
* Adds item types to a given entry.
*/

324
netwerk/cache/nsDiskCacheDeviceSQL.cpp поставляемый
Просмотреть файл

@ -59,10 +59,8 @@
#include "nsIVariant.h"
#include "nsThreadUtils.h"
#include "mozIStoragePendingStatement.h"
#include "mozIStorageService.h"
#include "mozIStorageStatement.h"
#include "mozIStorageStatementCallback.h"
#include "mozIStorageFunction.h"
#include "mozStorageHelper.h"
@ -135,11 +133,6 @@ class EvictionObserver
nsOfflineCacheEvictionFunction *evictionFunction)
: mDB(db), mEvictionFunction(evictionFunction)
{
if (mEvictionFunction->AddObserver() != 1) {
// not first observer
return;
}
mDB->ExecuteSimpleSQL(
NS_LITERAL_CSTRING("CREATE TEMP TRIGGER cache_on_delete AFTER DELETE"
" ON moz_cache FOR EACH ROW BEGIN SELECT"
@ -151,11 +144,6 @@ class EvictionObserver
~EvictionObserver()
{
if (mEvictionFunction->RemoveObserver() != 0) {
// not last observer
return;
}
mDB->ExecuteSimpleSQL(
NS_LITERAL_CSTRING("DROP TRIGGER cache_on_delete;"));
mEvictionFunction->Reset();
@ -186,157 +174,6 @@ DCacheHash(const char * key)
return (PRUint64(nsDiskCache::Hash(key, 0)) << 32) | nsDiskCache::Hash(key, 0x7416f295);
}
/**
* EvictAsyncHandler
*/
class EvictAsyncHandler : public mozIStorageStatementCallback
{
public:
NS_DECL_ISUPPORTS
NS_DECL_MOZISTORAGESTATEMENTCALLBACK
EvictAsyncHandler();
~EvictAsyncHandler();
nsresult Init(const char *aClientID,
nsIApplicationCacheAsyncCallback *aCallback,
mozIStorageConnection *aDB,
nsOfflineCacheEvictionFunction *aEvictionFunction) {
mClientID = NS_strdup(aClientID);
if (mClientID == NULL)
return NS_ERROR_OUT_OF_MEMORY;
mCallback = aCallback;
mDB = aDB;
mEvictionFunction = aEvictionFunction;
return NS_OK;
}
nsresult Start() {
mEvictionObserver = new EvictionObserver(mDB, mEvictionFunction);
HandleCompletion(mozIStorageStatementCallback::REASON_FINISHED);
return NS_OK;
}
private:
void ReportError() {
mCallback->HandleAsyncCompletion(nsIApplicationCacheAsyncCallback::APP_CACHE_REQUEST_ERROR);
}
void ReportSuccess() {
mCallback->HandleAsyncCompletion(nsIApplicationCacheAsyncCallback::APP_CACHE_REQUEST_SUCCESS);
}
private:
const char *mClientID;
nsCOMPtr<mozIStorageConnection> mDB;
nsCOMPtr<nsIApplicationCacheAsyncCallback> mCallback;
nsRefPtr<nsOfflineCacheEvictionFunction> mEvictionFunction;
EvictionObserver *mEvictionObserver;
/* Current step in the receipt to complete a eviction. */
int mStep;
};
NS_IMPL_ISUPPORTS1(EvictAsyncHandler, mozIStorageStatementCallback)
EvictAsyncHandler::EvictAsyncHandler() :
mClientID(NULL), mEvictionFunction(NULL), mStep(0)
{
}
EvictAsyncHandler::~EvictAsyncHandler() {
if (mClientID)
NS_Free((void *)mClientID);
if (mEvictionObserver)
delete mEvictionObserver;
}
NS_IMETHODIMP
EvictAsyncHandler::HandleResult(mozIStorageResultSet *aResultSet) {
return NS_OK;
}
NS_IMETHODIMP
EvictAsyncHandler::HandleError(mozIStorageError *aError) {
return NS_OK;
}
static nsresult
EvictEntriesSteps(mozIStorageConnection *mDB,
const char *clientID,
int step,
mozIStorageStatement **aStatement);
NS_IMETHODIMP
EvictAsyncHandler::HandleCompletion(unsigned short aReason) {
if (aReason != mozIStorageStatementCallback::REASON_FINISHED) {
mCallback->HandleAsyncCompletion(nsIApplicationCacheAsyncCallback::APP_CACHE_REQUEST_ERROR);
return NS_OK;
}
nsresult rv;
nsCOMPtr<mozIStorageStatement> statement;
rv = EvictEntriesSteps(mDB, mClientID, mStep++, getter_AddRefs(statement));
if (NS_FAILED(rv)) {
ReportError();
return NS_OK;
}
if (statement) {
nsCOMPtr<mozIStoragePendingStatement> pending;
rv = statement->ExecuteAsync(this, getter_AddRefs(pending));
if (NS_FAILED(rv)) {
ReportError();
}
} else {
// Complete the eviction, no more commands.
mEvictionObserver->Apply();
ReportSuccess();
}
return NS_OK;
}
/**
* RemoveFilesAsync removes files in a separated thread.
*/
class RemoveFilesAsync : public nsRunnable
{
public:
/**
* @param aItems is an array of nsIFile to remove.
*/
RemoveFilesAsync(nsCOMArray<nsIFile> &aItems) :
mItems(aItems) {}
~RemoveFilesAsync();
NS_IMETHOD Run();
private:
nsCOMArray<nsIFile> mItems;
nsCOMPtr<nsIThread> mIOThread;
};
RemoveFilesAsync::~RemoveFilesAsync() {
}
NS_IMETHODIMP
RemoveFilesAsync::Run() {
for (PRInt32 i = 0; i < mItems.Count(); i++) {
#if defined(PR_LOGGING)
nsCAutoString path;
mItems[i]->GetNativePath(path);
LOG((" removing %s\n", path.get()));
#endif
mItems[i]->Remove(false);
}
return NS_OK;
}
/******************************************************************************
* nsOfflineCacheEvictionFunction
*/
@ -404,17 +241,16 @@ nsOfflineCacheEvictionFunction::Apply()
{
LOG(("nsOfflineCacheEvictionFunction::Apply\n"));
if (!mIOThread) {
nsresult rv;
for (PRInt32 i = 0; i < mItems.Count(); i++) {
#if defined(PR_LOGGING)
nsCAutoString path;
mItems[i]->GetNativePath(path);
LOG((" removing %s\n", path.get()));
#endif
rv = NS_NewThread(getter_AddRefs(mIOThread));
NS_ASSERTION(NS_SUCCEEDED(rv), "fail to create a new thread");
mItems[i]->Remove(false);
}
nsCOMPtr<RemoveFilesAsync> removeFiles = new RemoveFilesAsync(mItems);
NS_ASSERTION(removeFiles, "fail to instantiate RemoveFilesAsync");
mIOThread->Dispatch(removeFiles, NS_DISPATCH_NORMAL);
Reset();
}
@ -863,22 +699,6 @@ nsApplicationCache::Discard()
return mDevice->EvictEntries(mClientID.get());
}
NS_IMETHODIMP
nsApplicationCache::DiscardAsync(nsIApplicationCacheAsyncCallback *aCallback)
{
NS_ENSURE_TRUE(mValid, NS_ERROR_NOT_AVAILABLE);
NS_ENSURE_TRUE(mDevice, NS_ERROR_NOT_AVAILABLE);
mValid = false;
if (mDevice->IsActiveCache(mGroup, mClientID))
{
mDevice->DeactivateGroup(mGroup);
}
return mDevice->EvictEntriesAsync(mClientID.get(), aCallback);
}
NS_IMETHODIMP
nsApplicationCache::MarkEntry(const nsACString &key,
PRUint32 typeBits)
@ -1912,102 +1732,82 @@ nsOfflineCacheDevice::Visit(nsICacheVisitor *visitor)
return NS_OK;
}
static const char *sEvictCmdsClientID[] = {
"DELETE FROM moz_cache WHERE ClientID=? AND Flags = 0;",
"DELETE FROM moz_cache_groups WHERE ActiveClientID=?;",
"DELETE FROM moz_cache_namespaces WHERE ClientID=?",
NULL
};
static const char *sEvictCmds[] = {
"DELETE FROM moz_cache WHERE Flags = 0;",
"DELETE FROM moz_cache_groups;",
"DELETE FROM moz_cache_namespaces;",
NULL
};
/**
* Create SQL statement for every step of eviction of cache entries.
*
* @param mDB is the database connection used for the eviction.
* @param clientID is the clientID of cache entries being evicting.
* @param step is the number of current step. (start from 0)
* @param statement is a pointer to return the stathement.
*/
static nsresult
EvictEntriesSteps(mozIStorageConnection *mDB,
const char *clientID,
int step,
mozIStorageStatement **aStatement)
{
const char **cmds = clientID ? sEvictCmdsClientID : sEvictCmds;
const char *cmd = cmds[step];
if (cmd == NULL) {
*aStatement = NULL;
return NS_OK;
}
// called to evict all entries matching the given clientID.
nsresult rv;
nsCOMPtr<mozIStorageStatement> statement;
rv = mDB->CreateStatement(nsDependentCString(cmd),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
if (clientID) {
rv = statement->BindUTF8StringByIndex(0, nsDependentCString(clientID));
NS_ENSURE_SUCCESS(rv, rv);
}
*aStatement = statement.forget().get();
return NS_OK;
}
nsresult
nsOfflineCacheDevice::EvictEntries(const char *clientID)
{
LOG(("nsOfflineCacheDevice::EvictEntries [cid=%s]\n",
clientID ? clientID : ""));
int step = 0;
nsresult rv = NS_OK;;
// called to evict all entries matching the given clientID.
// need trigger to fire user defined function after a row is deleted
// so we can delete the corresponding data file.
EvictionObserver evictionObserver(mDB, mEvictionFunction);
nsCOMPtr<mozIStorageStatement> statement;
while (1) {
rv = EvictEntriesSteps(mDB, clientID, step++, getter_AddRefs(statement));
if (NS_FAILED(rv)) break;
nsresult rv;
if (clientID)
{
rv = mDB->CreateStatement(NS_LITERAL_CSTRING("DELETE FROM moz_cache WHERE ClientID=? AND Flags = 0;"),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
if (!statement) break; // finish
rv = statement->BindUTF8StringByIndex(0, nsDependentCString(clientID));
NS_ENSURE_SUCCESS(rv, rv);
statement->Execute();
if (NS_FAILED(rv)) break;
rv = statement->Execute();
NS_ENSURE_SUCCESS(rv, rv);
rv = mDB->CreateStatement(NS_LITERAL_CSTRING("DELETE FROM moz_cache_groups WHERE ActiveClientID=?;"),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
rv = statement->BindUTF8StringByIndex(0, nsDependentCString(clientID));
NS_ENSURE_SUCCESS(rv, rv);
rv = statement->Execute();
NS_ENSURE_SUCCESS(rv, rv);
}
else
{
rv = mDB->CreateStatement(NS_LITERAL_CSTRING("DELETE FROM moz_cache WHERE Flags = 0;"),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
rv = statement->Execute();
NS_ENSURE_SUCCESS(rv, rv);
rv = mDB->CreateStatement(NS_LITERAL_CSTRING("DELETE FROM moz_cache_groups;"),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
rv = statement->Execute();
NS_ENSURE_SUCCESS(rv, rv);
}
evictionObserver.Apply();
return rv;
}
statement = nsnull;
// Also evict any namespaces associated with this clientID.
if (clientID)
{
rv = mDB->CreateStatement(NS_LITERAL_CSTRING("DELETE FROM moz_cache_namespaces WHERE ClientID=?"),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
nsresult
nsOfflineCacheDevice::EvictEntriesAsync(const char *clientID,
nsIApplicationCacheAsyncCallback *aCallback)
{
LOG(("nsOfflineCacheDevice::EvictEntriesAsync [cid=%s]\n",
clientID ? clientID : ""));
rv = statement->BindUTF8StringByIndex(0, nsDependentCString(clientID));
NS_ENSURE_SUCCESS(rv, rv);
}
else
{
rv = mDB->CreateStatement(NS_LITERAL_CSTRING("DELETE FROM moz_cache_namespaces;"),
getter_AddRefs(statement));
NS_ENSURE_SUCCESS(rv, rv);
}
EvictAsyncHandler *evictAsyncHandler = new EvictAsyncHandler();
if (evictAsyncHandler == NULL)
return NS_ERROR_OUT_OF_MEMORY;
rv = statement->Execute();
NS_ENSURE_SUCCESS(rv, rv);
evictAsyncHandler->Init(clientID, aCallback, mDB, mEvictionFunction);
evictAsyncHandler->Start();
return NS_OK;
}

10
netwerk/cache/nsDiskCacheDeviceSQL.h поставляемый
Просмотреть файл

@ -77,21 +77,14 @@ public:
nsOfflineCacheEvictionFunction(nsOfflineCacheDevice *device)
: mDevice(device)
, mObserverCount(0)
{}
void Reset() { mItems.Clear(); }
void Apply();
int AddObserver() { return ++mObserverCount; }
int RemoveObserver() { return --mObserverCount; }
private:
nsOfflineCacheDevice *mDevice;
nsCOMArray<nsIFile> mItems;
nsCOMPtr<nsIThread> mIOThread;
int mObserverCount;
};
@ -138,9 +131,6 @@ public:
virtual nsresult EvictEntries(const char * clientID);
virtual nsresult EvictEntriesAsync(const char * clientID,
nsIApplicationCacheAsyncCallback *aCallback);
/* Entry ownership */
nsresult GetOwnerDomains(const char * clientID,
PRUint32 * count,

Просмотреть файл

@ -1125,10 +1125,9 @@ nsOfflineManifestItem::OnStopRequest(nsIRequest *aRequest,
// nsOfflineCacheUpdate::nsISupports
//-----------------------------------------------------------------------------
NS_IMPL_ISUPPORTS3(nsOfflineCacheUpdate,
NS_IMPL_ISUPPORTS2(nsOfflineCacheUpdate,
nsIOfflineCacheUpdateObserver,
nsIOfflineCacheUpdate,
nsIApplicationCacheAsyncCallback)
nsIOfflineCacheUpdate)
//-----------------------------------------------------------------------------
// nsOfflineCacheUpdate <public>
@ -1448,15 +1447,26 @@ nsOfflineCacheUpdate::LoadCompleted()
mPinnedEntryRetriesCount < kPinnedEntryRetriesLimit &&
(item->mItemType & (nsIApplicationCache::ITEM_EXPLICIT |
nsIApplicationCache::ITEM_FALLBACK))) {
rv = item->Cancel();
if (NS_SUCCEEDED(rv)) {
mPinnedEntryRetriesCount++;
// Do a retrying for current item, so mCurrentItem is not advanced.
rv = EvictOneNonPinnedAsync();
rv = EvictOneNonPinned();
if (NS_FAILED(rv)) {
mSucceeded = false;
NotifyState(nsIOfflineCacheUpdateObserver::STATE_ERROR);
Finish();
return;
}
if (NS_SUCCEEDED(rv)) return;
rv = item->Cancel();
if (NS_FAILED(rv)) {
mSucceeded = false;
NotifyState(nsIOfflineCacheUpdateObserver::STATE_ERROR);
Finish();
return;
}
mPinnedEntryRetriesCount++;
// Retry current item, so mCurrentItem is not advanced.
ProcessNextURI();
return;
}
}
@ -1881,8 +1891,7 @@ nsOfflineCacheUpdate::Finish()
static nsresult
EvictOneOfCacheGroups(nsIApplicationCacheService *cacheService,
PRUint32 count, const char * const *groups,
nsIApplicationCacheAsyncCallback *aCallback)
PRUint32 count, const char * const *groups)
{
nsresult rv;
unsigned int i;
@ -1906,24 +1915,16 @@ EvictOneOfCacheGroups(nsIApplicationCacheService *cacheService,
NS_ENSURE_SUCCESS(rv, rv);
if (!pinned) {
// Call HandleAsyncCompletion() when the task is completed.
rv = cache->DiscardAsync(aCallback);
return NS_OK;
rv = cache->Discard();
return NS_OK;
}
}
return NS_ERROR_FILE_NOT_FOUND;
}
/**
* Evict one of non-pinned cache group in asynchronized.
*
* This method returns immediately. It will start an async task to
* evict a selected cache group. HandleAsyncCompletion() will be
* called while the eviction is completed.
*/
nsresult
nsOfflineCacheUpdate::EvictOneNonPinnedAsync()
nsresult
nsOfflineCacheUpdate::EvictOneNonPinned()
{
nsresult rv;
@ -1936,7 +1937,7 @@ nsOfflineCacheUpdate::EvictOneNonPinnedAsync()
rv = cacheService->GetGroupsTimeOrdered(&count, &groups);
NS_ENSURE_SUCCESS(rv, rv);
rv = EvictOneOfCacheGroups(cacheService, count, groups, this);
rv = EvictOneOfCacheGroups(cacheService, count, groups);
NS_FREE_XPCOM_ALLOCATED_POINTER_ARRAY(count, groups);
return rv;
@ -2158,19 +2159,3 @@ nsOfflineCacheUpdate::ApplicationCacheAvailable(nsIApplicationCache *application
{
return AssociateDocuments(applicationCache);
}
//-----------------------------------------------------------------------------
// nsOfflineCacheUpdate::nsIApplicationCacheAsyncCallback
//-----------------------------------------------------------------------------
NS_IMETHODIMP
nsOfflineCacheUpdate::HandleAsyncCompletion(PRUint32 aState) {
if (aState != APP_CACHE_REQUEST_SUCCESS) {
mSucceeded = false;
NotifyState(nsIOfflineCacheUpdateObserver::STATE_ERROR);
Finish();
return NS_OK;
}
return ProcessNextURI();
}

Просмотреть файл

@ -213,13 +213,11 @@ public:
class nsOfflineCacheUpdate : public nsIOfflineCacheUpdate
, public nsIOfflineCacheUpdateObserver
, public nsOfflineCacheUpdateOwner
, public nsIApplicationCacheAsyncCallback
{
public:
NS_DECL_ISUPPORTS
NS_DECL_NSIOFFLINECACHEUPDATE
NS_DECL_NSIOFFLINECACHEUPDATEOBSERVER
NS_DECL_NSIAPPLICATIONCACHEASYNCCALLBACK
nsOfflineCacheUpdate();
~nsOfflineCacheUpdate();
@ -260,7 +258,7 @@ private:
nsresult FinishNoNotify();
// Find one non-pinned cache group and evict it.
nsresult EvictOneNonPinnedAsync();
nsresult EvictOneNonPinned();
enum {
STATE_UNINITIALIZED,