Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 #include "storage/browser/blob/blob_flattener.h" | |
| 6 | |
| 7 #include <limits> | |
| 8 #include <set> | |
| 9 #include <utility> | |
| 10 | |
| 11 #include "storage/browser/blob/blob_async_transport_request_builder.h" | |
| 12 #include "storage/browser/blob/blob_data_builder.h" | |
| 13 #include "storage/browser/blob/blob_slice.h" | |
| 14 #include "storage/browser/blob/blob_storage_context.h" | |
| 15 #include "storage/browser/blob/blob_storage_registry.h" | |
| 16 #include "storage/browser/blob/shareable_blob_data_item.h" | |
| 17 | |
| 18 namespace storage { | |
| 19 namespace { | |
| 20 using ItemCopyEntry = BlobStorageRegistry::ItemCopyEntry; | |
| 21 using BlobEntry = BlobStorageRegistry::Entry; | |
| 22 | |
| 23 bool IsBytes(DataElement::Type type) { | |
| 24 return type == DataElement::TYPE_BYTES || | |
| 25 type == DataElement::TYPE_BYTES_DESCRIPTION; | |
| 26 } | |
| 27 | |
| 28 } // namespace | |
| 29 | |
| 30 // static | |
| 31 BlobFlattener::BlobFlattener(const BlobDataBuilder& transportation_result, | |
| 32 InternalBlobData* output_blob, | |
| 33 BlobStorageRegistry* registry) { | |
| 34 const std::vector<scoped_refptr<BlobDataItem>>& transport_items = | |
| 35 transportation_result.items_; | |
| 36 const std::string& uuid = transportation_result.uuid_; | |
| 37 | |
| 38 std::set<std::string> dependent_blob_uuids; | |
| 39 for (scoped_refptr<BlobDataItem> transport_item : transport_items) { | |
| 40 DataElement::Type type = transport_item->type(); | |
| 41 contains_pending_content |= type == DataElement::TYPE_BYTES_DESCRIPTION; | |
| 42 | |
| 43 if (IsBytes(type)) { | |
| 44 memory_needed += transport_item->length(); | |
| 45 total_size += transport_item->length(); | |
| 46 output_blob->AppendSharedBlobItem( | |
| 47 uuid, new ShareableBlobDataItem(std::move(transport_item))); | |
|
kinuko
2016/07/17 16:15:46
if we continue here and the following 'else if' ca
dmurph
2016/07/19 02:26:27
Done.
| |
| 48 } else if (type == DataElement::TYPE_BLOB) { | |
| 49 BlobEntry* ref_entry = registry->GetEntry(transport_item->blob_uuid()); | |
| 50 | |
| 51 if (!ref_entry || BlobStatusIsError(ref_entry->status) || | |
| 52 transport_item->blob_uuid() == uuid) { | |
| 53 contains_broken_references = true; | |
| 54 return; | |
| 55 } | |
| 56 | |
| 57 if (dependent_blob_uuids.find(transport_item->blob_uuid()) == | |
| 58 dependent_blob_uuids.end()) { | |
| 59 dependent_blobs.push_back( | |
| 60 std::make_pair(transport_item->blob_uuid(), ref_entry)); | |
| 61 dependent_blob_uuids.insert(transport_item->blob_uuid()); | |
| 62 } | |
| 63 | |
| 64 uint64_t length = transport_item->length() == DataElement::kUnknownSize | |
| 65 ? ref_entry->data.total_size() | |
| 66 : transport_item->length(); | |
| 67 total_size += length; | |
| 68 | |
| 69 // If we're referencing the whole blob, then we don't need to slice. | |
| 70 if (transport_item->offset() == 0 && | |
| 71 length == ref_entry->data.total_size()) { | |
| 72 for (const auto& shareable_item : ref_entry->data.items()) { | |
| 73 output_blob->AppendSharedBlobItem(uuid, shareable_item); | |
| 74 } | |
| 75 continue; | |
| 76 } | |
| 77 | |
| 78 // Validate our reference has good offset & length. | |
| 79 if (transport_item->offset() + transport_item->length() > | |
| 80 ref_entry->data.total_size()) { | |
| 81 contains_invalid_references = true; | |
| 82 return; | |
| 83 } | |
| 84 | |
| 85 BlobSlice slice(ref_entry->data, transport_item->offset(), | |
| 86 transport_item->length()); | |
| 87 | |
| 88 if (slice.first_source_item) { | |
| 89 copies.push_back(ItemCopyEntry(slice.first_source_item, | |
| 90 slice.first_item_slice_offset, | |
| 91 slice.dest_items.front())); | |
| 92 } | |
| 93 if (slice.last_source_item) { | |
| 94 copies.push_back( | |
| 95 ItemCopyEntry(slice.last_source_item, 0, slice.dest_items.back())); | |
| 96 } | |
| 97 | |
| 98 memory_needed += slice.copying_memory_size; | |
| 99 for (auto& shareable_item : slice.dest_items) { | |
| 100 output_blob->AppendSharedBlobItem(uuid, std::move(shareable_item)); | |
| 101 } | |
|
kinuko
2016/07/17 16:15:46
ditto, continue here and move out the following co
dmurph
2016/07/19 02:26:27
Done.
| |
| 102 } else { | |
| 103 if (type == DataElement::TYPE_FILE) { | |
| 104 contains_pending_content |= | |
| 105 transport_item->path().value() == | |
| 106 BlobDataBuilder::kAppendFutureFileTemporaryFileName; | |
| 107 } | |
| 108 total_size += transport_item->length(); | |
| 109 output_blob->AppendSharedBlobItem( | |
| 110 uuid, new ShareableBlobDataItem(std::move(transport_item))); | |
| 111 } | |
| 112 } | |
| 113 } | |
| 114 | |
| 115 BlobFlattener::~BlobFlattener() {} | |
| 116 | |
| 117 } // namespace storage | |
| OLD | NEW |