From dd9a4f3f1d66afcf896ba114c476a7c008989ce5 Mon Sep 17 00:00:00 2001 From: "darin%netscape.com" Date: Wed, 27 Jun 2001 02:30:18 +0000 Subject: [PATCH] Fixes bug 82418 "URL makes mozilla totally unresponsive" patch=gordon r/sr=dougt,darin --- netwerk/cache/src/nsCacheService.cpp | 46 ++++++++++++++++----- netwerk/protocol/http/src/nsHttpChannel.cpp | 3 ++ 2 files changed, 39 insertions(+), 10 deletions(-) diff --git a/netwerk/cache/src/nsCacheService.cpp b/netwerk/cache/src/nsCacheService.cpp index d233faeecc55..052856edaecd 100644 --- a/netwerk/cache/src/nsCacheService.cpp +++ b/netwerk/cache/src/nsCacheService.cpp @@ -1018,20 +1018,44 @@ nsCacheService::DeactivateEntry(nsCacheEntry * entry) nsresult nsCacheService::ProcessPendingRequests(nsCacheEntry * entry) { - nsresult rv = NS_OK; + nsresult rv = NS_OK; + nsCacheRequest * request = (nsCacheRequest *)PR_LIST_HEAD(&entry->mRequestQ); + nsCacheRequest * nextRequest; + PRBool newWriter = PR_FALSE; + + if (request == &entry->mRequestQ) return NS_OK; // no queued requests if (!entry->IsDoomed() && entry->IsInvalid()) { // 1st descriptor closed w/o MarkValid() - // XXX assert no open descriptors - // XXX find best requests to promote to 1st Writer - // XXX process ACCESS_WRITE (shouldn't have any of these) - // XXX ACCESS_READ_WRITE, ACCESS_READ - NS_ASSERTION(PR_TRUE, - "closing descriptors w/o calling MarkValid is not supported yet."); + NS_ASSERTION(PR_CLIST_IS_EMPTY(&entry->mDescriptorQ), "shouldn't be here with open descriptors"); + +#if DEBUG + // verify no ACCESS_WRITE requests(shouldn't have any of these) + while (request != &entry->mRequestQ) { + NS_ASSERTION(request->AccessRequested() != nsICache::ACCESS_WRITE, + "ACCESS_WRITE request should have been given a new entry"); + request = (nsCacheRequest *)PR_NEXT_LINK(request); + } + request = (nsCacheRequest *)PR_LIST_HEAD(&entry->mRequestQ); +#endif + // find first request with ACCESS_READ_WRITE (if any) and promote it to 1st writer + while (request != &entry->mRequestQ) { + if (request->AccessRequested() == nsICache::ACCESS_READ_WRITE) { + newWriter = PR_TRUE; + break; + } + + request = (nsCacheRequest *)PR_NEXT_LINK(request); + } + + if (request == &entry->mRequestQ) // no requests asked for ACCESS_READ_WRITE, back to top + request = (nsCacheRequest *)PR_LIST_HEAD(&entry->mRequestQ); + + // XXX what should we do if there are only READ requests in queue? + // XXX serialize their accesses, give them only read access, but force them to check validate flag? + // XXX or do readers simply presume the entry is valid } - nsCacheRequest * request = (nsCacheRequest *)PR_LIST_HEAD(&entry->mRequestQ); - nsCacheRequest * nextRequest; nsCacheAccessMode accessGranted = nsICache::ACCESS_NONE; while (request != &entry->mRequestQ) { @@ -1052,10 +1076,11 @@ nsCacheService::ProcessPendingRequests(nsCacheEntry * entry) if (NS_FAILED(rv)) { // XXX what to do? } - } else if (entry->IsValid()) { + } else if (entry->IsValid() || newWriter) { rv = entry->RequestAccess(request, &accessGranted); NS_ASSERTION(NS_SUCCEEDED(rv), "if entry is valid, RequestAccess must succeed."); + // XXX if (newWriter) NS_ASSERTION( accessGranted == request->AccessRequested(), "why not?"); // entry->CreateDescriptor dequeues request, and queues descriptor nsCOMPtr descriptor; @@ -1078,6 +1103,7 @@ nsCacheService::ProcessPendingRequests(nsCacheEntry * entry) // Synchronous request request->WakeUp(); } + if (newWriter) break; // process remaining requests after validation request = nextRequest; } diff --git a/netwerk/protocol/http/src/nsHttpChannel.cpp b/netwerk/protocol/http/src/nsHttpChannel.cpp index 69e4c4e8ad9c..2b2a072b7b6a 100644 --- a/netwerk/protocol/http/src/nsHttpChannel.cpp +++ b/netwerk/protocol/http/src/nsHttpChannel.cpp @@ -2100,8 +2100,11 @@ nsHttpChannel::OnStopRequest(nsIRequest *request, nsISupports *ctxt, nsresult st mTransaction = nsnull; } + // we don't support overlapped i/o (bug 82418) +#if 0 if (mCacheEntry && NS_SUCCEEDED(status)) mCacheEntry->MarkValid(); +#endif if (mListener) { mListener->OnStopRequest(this, mListenerContext, status);