summaryrefslogtreecommitdiffstats
path: root/net/http/partial_data.cc
diff options
context:
space:
mode:
authorrvargas@google.com <rvargas@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2009-08-12 00:14:48 +0000
committerrvargas@google.com <rvargas@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2009-08-12 00:14:48 +0000
commit44f873a6f7b7b9778756b57d59c6a8d43f696bde (patch)
tree0ea01098e650aee927a61c3de5ea4f2fccd37269 /net/http/partial_data.cc
parent5506e7813e6ab6330665ae8cc5fb3cc8275d90ff (diff)
downloadchromium_src-44f873a6f7b7b9778756b57d59c6a8d43f696bde.zip
chromium_src-44f873a6f7b7b9778756b57d59c6a8d43f696bde.tar.gz
chromium_src-44f873a6f7b7b9778756b57d59c6a8d43f696bde.tar.bz2
Http cache: Extend support for byte range requests.
* Now we handle regular requests (not byte range requests) that end up reading a cached entry that stores byte ranges. In this case we create a control object (partial_), but it's byte_range_ member is always invalid because the user is not requesting a range. * Given that we may find stored 206s that are not keeping sparse data, we detect that case and handle it. * Now we may end up reading 206 from disk (and the net) and having to change the returned status to be 200 (for regular requests). * We avoid performing re-validations for each piece of stored data. Instead, we consider the whole entry to be revalidated once, and read from the cache without asking the server (as far as we can). * When processing the received headers we now consider receiving 200 and 416 (instead of 206/304) and we handle inconsistencies in the range returned by the server (from what we expect). We also handle receiving 206 when we don't expect it. BUG=12258 TEST=unittests Review URL: http://codereview.chromium.org/164304 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@23123 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'net/http/partial_data.cc')
-rw-r--r--net/http/partial_data.cc53
1 files changed, 36 insertions, 17 deletions
diff --git a/net/http/partial_data.cc b/net/http/partial_data.cc
index 8d56966..a4d5976 100644
--- a/net/http/partial_data.cc
+++ b/net/http/partial_data.cc
@@ -53,7 +53,7 @@ int PartialData::PrepareCacheValidation(disk_cache::Entry* entry,
// Scan the disk cache for the first cached portion within this range.
int64 range_len = byte_range_.HasLastBytePosition() ?
- byte_range_.last_byte_position() - current_range_start_ + 1: kint32max;
+ byte_range_.last_byte_position() - current_range_start_ + 1 : kint32max;
if (range_len > kint32max)
range_len = kint32max;
int len = static_cast<int32>(range_len);
@@ -100,20 +100,32 @@ bool PartialData::IsLastRange() const {
return final_range_;
}
-bool PartialData::UpdateFromStoredHeaders(const HttpResponseHeaders* headers) {
+bool PartialData::UpdateFromStoredHeaders(const HttpResponseHeaders* headers,
+ disk_cache::Entry* entry) {
std::string length_value;
resource_size_ = 0;
if (!headers->GetNormalizedHeader(kLengthHeader, &length_value))
return false; // We must have stored the resource length.
- if (!StringToInt64(length_value, &resource_size_))
+ if (!StringToInt64(length_value, &resource_size_) || !resource_size_)
return false;
- if (resource_size_ && !byte_range_.ComputeBounds(resource_size_))
- return false;
+ if (byte_range_.IsValid()) {
+ if (!byte_range_.ComputeBounds(resource_size_))
+ return false;
+
+ if (current_range_start_ < 0)
+ current_range_start_ = byte_range_.first_byte_position();
+ } else {
+ // This is not a range request but we have partial data stored.
+ current_range_start_ = 0;
+ byte_range_.set_last_byte_position(resource_size_ - 1);
+ }
- if (current_range_start_ < 0)
- current_range_start_ = byte_range_.first_byte_position();
+ // Make sure that this is really a sparse entry.
+ int64 n;
+ if (ERR_CACHE_OPERATION_NOT_SUPPORTED == entry->GetAvailableRange(0, 5, &n))
+ return false;
return current_range_start_ >= 0;
}
@@ -141,7 +153,7 @@ bool PartialData::ResponseHeadersOK(const HttpResponseHeaders* headers) {
if (start != current_range_start_)
return false;
- if (end > byte_range_.last_byte_position())
+ if (byte_range_.IsValid() && end > byte_range_.last_byte_position())
return false;
return true;
@@ -154,15 +166,23 @@ void PartialData::FixResponseHeaders(HttpResponseHeaders* headers) {
headers->RemoveHeader(kLengthHeader);
headers->RemoveHeader(kRangeHeader);
- DCHECK(byte_range_.HasFirstBytePosition());
- DCHECK(byte_range_.HasLastBytePosition());
- headers->AddHeader(StringPrintf("%s: bytes %lld-%lld/%lld", kRangeHeader,
- byte_range_.first_byte_position(),
- byte_range_.last_byte_position(),
- resource_size_));
+ int64 range_len;
+ if (byte_range_.IsValid()) {
+ DCHECK(byte_range_.HasFirstBytePosition());
+ DCHECK(byte_range_.HasLastBytePosition());
+ headers->AddHeader(StringPrintf("%s: bytes %lld-%lld/%lld", kRangeHeader,
+ byte_range_.first_byte_position(),
+ byte_range_.last_byte_position(),
+ resource_size_));
+ range_len = byte_range_.last_byte_position() -
+ byte_range_.first_byte_position() + 1;
+ } else {
+ // TODO(rvargas): Is it safe to change the protocol version?
+ headers->ReplaceStatusLine("HTTP/1.1 200 OK");
+ DCHECK_NE(resource_size_, 0);
+ range_len = resource_size_;
+ }
- int64 range_len = byte_range_.last_byte_position() -
- byte_range_.first_byte_position() + 1;
headers->AddHeader(StringPrintf("%s: %lld", kLengthHeader, range_len));
}
@@ -214,5 +234,4 @@ void PartialData::AddRangeHeader(int64 start, int64 end, std::string* headers) {
my_end.c_str()));
}
-
} // namespace net