Chromium Code Reviews| Index: content/browser/appcache/appcache_response.cc |
| diff --git a/content/browser/appcache/appcache_response.cc b/content/browser/appcache/appcache_response.cc |
| index c38d3afa29305830e595b4c4adeb95207bf50f02..da055236b86b2891757e07eae7a7d8945d059da9 100644 |
| --- a/content/browser/appcache/appcache_response.cc |
| +++ b/content/browser/appcache/appcache_response.cc |
| @@ -22,10 +22,7 @@ namespace content { |
| namespace { |
| // Disk cache entry data indices. |
| -enum { |
| - kResponseInfoIndex, |
| - kResponseContentIndex |
| -}; |
| +enum { kResponseInfoIndex, kResponseContentIndex, kResponseMetadataIndex }; |
| // An IOBuffer that wraps a pickle's data. Ownership of the |
| // pickle is transfered to the WrappedPickleIOBuffer object. |
| @@ -143,11 +140,14 @@ void AppCacheResponseIO::OnRawIOComplete(int result) { |
| // AppCacheResponseReader ---------------------------------------------- |
| AppCacheResponseReader::AppCacheResponseReader( |
| - int64 response_id, int64 group_id, AppCacheDiskCacheInterface* disk_cache) |
| + int64 response_id, |
| + int64 group_id, |
| + AppCacheDiskCacheInterface* disk_cache) |
| : AppCacheResponseIO(response_id, group_id, disk_cache), |
| range_offset_(0), |
| range_length_(kint32max), |
| read_position_(0), |
| + reading_metadata_size_(0), |
| weak_factory_(this) { |
| } |
| @@ -224,7 +224,11 @@ void AppCacheResponseReader::SetReadRange(int offset, int length) { |
| void AppCacheResponseReader::OnIOComplete(int result) { |
| if (result >= 0) { |
| - if (info_buffer_.get()) { |
| + if (reading_metadata_size_) { |
| + DCHECK(reading_metadata_size_ == result); |
| + DCHECK(info_buffer_->http_info->metadata); |
| + reading_metadata_size_ = 0; |
| + } else if (info_buffer_.get()) { |
| // Deserialize the http info structure, ensuring we got headers. |
| Pickle pickle(buffer_->data(), result); |
| scoped_ptr<net::HttpResponseInfo> info(new net::HttpResponseInfo); |
| @@ -241,6 +245,16 @@ void AppCacheResponseReader::OnIOComplete(int result) { |
| DCHECK(entry_); |
| info_buffer_->response_data_size = |
| entry_->GetSize(kResponseContentIndex); |
| + |
| + int64 metadata_size = entry_->GetSize(kResponseMetadataIndex); |
| + if (metadata_size > 0) { |
| + reading_metadata_size_ = metadata_size; |
| + info_buffer_->http_info->metadata = |
| + new net::IOBufferWithSize(metadata_size); |
| + ReadRaw(kResponseMetadataIndex, 0, |
| + info_buffer_->http_info->metadata.get(), metadata_size); |
| + return; |
| + } |
| } else { |
| read_position_ += result; |
| } |
| @@ -426,4 +440,74 @@ void AppCacheResponseWriter::OnCreateEntryComplete( |
| ContinueWriteData(); |
| } |
| +// AppCacheResponseMetadataWriter ---------------------------------------------- |
| + |
| +AppCacheResponseMetadataWriter::AppCacheResponseMetadataWriter( |
| + int64 response_id, |
| + int64 group_id, |
| + AppCacheDiskCacheInterface* disk_cache) |
| + : AppCacheResponseIO(response_id, group_id, disk_cache), |
| + started_(false), |
| + write_amount_(0), |
| + weak_factory_(this) { |
| +} |
| + |
| +AppCacheResponseMetadataWriter::~AppCacheResponseMetadataWriter() { |
| +} |
| + |
| +void AppCacheResponseMetadataWriter::WriteMetadata( |
| + net::IOBuffer* buf, |
| + int buf_len, |
| + const net::CompletionCallback& callback) { |
| + DCHECK(!callback.is_null()); |
| + DCHECK(!IsIOPending()); |
| + DCHECK(buf); |
| + DCHECK(buf_len >= 0); |
| + DCHECK(!buffer_.get()); |
| + DCHECK(!started_); |
| + |
| + started_ = true; |
| + buffer_ = buf; |
| + write_amount_ = buf_len; |
| + callback_ = callback; // cleared on completion |
| + OpenEntry(); |
| +} |
| + |
| +void AppCacheResponseMetadataWriter::OpenEntry() { |
|
michaeln
2015/02/18 02:18:59
It'd be nice to hoist this method and the followin
horo
2015/02/18 03:33:44
Sounds good!
done.
|
| + int rv; |
| + DCHECK(!entry_); |
| + DCHECK(disk_cache_); |
| + AppCacheDiskCacheInterface::Entry** entry_ptr = |
| + new AppCacheDiskCacheInterface::Entry*; |
| + open_callback_ = |
| + base::Bind(&AppCacheResponseMetadataWriter::OnOpenEntryComplete, |
| + weak_factory_.GetWeakPtr(), base::Owned(entry_ptr)); |
| + rv = disk_cache_->OpenEntry(response_id_, entry_ptr, open_callback_); |
| + if (rv != net::ERR_IO_PENDING) |
| + OnOpenEntryComplete(entry_ptr, rv); |
| +} |
| + |
| +void AppCacheResponseMetadataWriter::OnOpenEntryComplete( |
| + AppCacheDiskCacheInterface::Entry** entry, |
| + int rv) { |
| + DCHECK(buffer_.get()); |
| + if (!open_callback_.is_null()) { |
| + if (rv == net::OK) { |
| + DCHECK(entry); |
| + entry_ = *entry; |
| + } |
| + open_callback_.Reset(); |
| + } |
| + if (!entry_) { |
| + ScheduleIOCompletionCallback(net::ERR_FAILED); |
| + return; |
| + } |
| + WriteRaw(kResponseMetadataIndex, 0, buffer_.get(), write_amount_); |
|
michaeln
2015/02/18 02:18:59
and have it call a virtual method here to continue
horo
2015/02/18 03:33:44
Done.
|
| +} |
| + |
| +void AppCacheResponseMetadataWriter::OnIOComplete(int result) { |
| + DCHECK(result < 0 || write_amount_ == result); |
| + InvokeUserCompletionCallback(result); |
| +} |
| + |
| } // namespace content |