зеркало из https://github.com/mozilla/gecko-dev.git
[not part of build]
Fix race condition in nsCacheRequest WaitForValidation(). Force !streamBased to set storagePolicy to nsICache:STORE_IN_MEMORY when creating nsCacheSessions. Fix ProcessRequest() to refrain from creating a descriptor for ACCESS_READ requests when no entry is found (found by pavlov).
This commit is contained in:
Родитель
83bbffbccd
Коммит
a73e430dc1
|
@ -54,6 +54,7 @@ private:
|
|||
SetAccessRequested(accessRequested);
|
||||
if (streamBased) MarkStreamBased();
|
||||
SetStoragePolicy(storagePolicy);
|
||||
MarkWaitingForValidation();
|
||||
}
|
||||
|
||||
~nsCacheRequest()
|
||||
|
@ -111,6 +112,11 @@ private:
|
|||
nsresult
|
||||
WaitForValidation(void)
|
||||
{
|
||||
if (!WaitingForValidation()) { // flag already cleared
|
||||
MarkWaitingForValidation(); // set up for next time
|
||||
return NS_OK; // early exit;
|
||||
}
|
||||
|
||||
if (!mLock) {
|
||||
mLock = PR_NewLock();
|
||||
if (!mLock) return NS_ERROR_OUT_OF_MEMORY;
|
||||
|
@ -122,14 +128,14 @@ private:
|
|||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
}
|
||||
}
|
||||
|
||||
PRStatus status;
|
||||
PR_Lock(mLock);
|
||||
while (WaitingForValidation() && (status == PR_SUCCESS) ) {
|
||||
status = PR_WaitCondVar(mCondVar, PR_INTERVAL_NO_TIMEOUT);
|
||||
}
|
||||
MarkWaitingForValidation(); // set up for next time
|
||||
PR_Unlock(mLock);
|
||||
|
||||
|
||||
NS_ASSERTION(status == PR_SUCCESS, "PR_WaitCondVar() returned PR_FAILURE?");
|
||||
if (status == PR_FAILURE)
|
||||
return NS_ERROR_UNEXPECTED;
|
||||
|
@ -138,10 +144,12 @@ private:
|
|||
}
|
||||
|
||||
void WakeUp(void) {
|
||||
PR_Lock(mLock);
|
||||
DoneWaitingForValidation();
|
||||
if (mLock) {
|
||||
PR_Lock(mLock);
|
||||
PR_NotifyCondVar(mCondVar);
|
||||
PR_Unlock(mLock);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -282,6 +282,7 @@ nsCacheService::ProcessRequest(nsCacheRequest * request,
|
|||
if (request->mListener) // async exits - validate, doom, or close will resume
|
||||
return rv;
|
||||
|
||||
// XXX allocate condvar for request if necessary
|
||||
PR_Unlock(mCacheServiceLock);
|
||||
rv = request->WaitForValidation();
|
||||
PR_Lock(mCacheServiceLock);
|
||||
|
@ -300,8 +301,9 @@ nsCacheService::ProcessRequest(nsCacheRequest * request,
|
|||
}
|
||||
|
||||
nsCOMPtr<nsICacheEntryDescriptor> descriptor;
|
||||
|
||||
rv = entry->CreateDescriptor(request, accessGranted, getter_AddRefs(descriptor));
|
||||
|
||||
if (NS_SUCCEEDED(rv))
|
||||
rv = entry->CreateDescriptor(request, accessGranted, getter_AddRefs(descriptor));
|
||||
|
||||
if (request->mListener) { // Asynchronous
|
||||
// call listener to report error or descriptor
|
||||
|
|
|
@ -38,6 +38,7 @@ nsCacheSession::nsCacheSession(const char * clientID,
|
|||
mStreamBased(streamBased)
|
||||
{
|
||||
NS_INIT_ISUPPORTS();
|
||||
if (!streamBased) mStoragePolicy = nsICache::STORE_IN_MEMORY;
|
||||
}
|
||||
|
||||
nsCacheSession::~nsCacheSession()
|
||||
|
|
Загрузка…
Ссылка в новой задаче