OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "content/browser/frame_host/navigation_entry_impl.h" | 5 #include "content/browser/frame_host/navigation_entry_impl.h" |
6 | 6 |
7 #include <queue> | 7 #include <queue> |
8 | 8 |
9 #include "base/metrics/histogram.h" | 9 #include "base/metrics/histogram.h" |
10 #include "base/strings/string_util.h" | 10 #include "base/strings/string_util.h" |
11 #include "base/strings/utf_string_conversions.h" | 11 #include "base/strings/utf_string_conversions.h" |
12 #include "components/url_formatter/url_formatter.h" | 12 #include "components/url_formatter/url_formatter.h" |
13 #include "content/common/navigation_params.h" | 13 #include "content/common/navigation_params.h" |
14 #include "content/common/page_state_serialization.h" | 14 #include "content/common/page_state_serialization.h" |
15 #include "content/common/site_isolation_policy.h" | 15 #include "content/common/site_isolation_policy.h" |
16 #include "content/public/common/content_constants.h" | 16 #include "content/public/common/content_constants.h" |
17 #include "content/public/common/url_constants.h" | 17 #include "content/public/common/url_constants.h" |
18 #include "ui/gfx/text_elider.h" | 18 #include "ui/gfx/text_elider.h" |
19 | 19 |
| 20 using base::UTF16ToUTF8; |
| 21 |
| 22 namespace content { |
| 23 |
| 24 namespace { |
| 25 |
20 // Use this to get a new unique ID for a NavigationEntry during construction. | 26 // Use this to get a new unique ID for a NavigationEntry during construction. |
21 // The returned ID is guaranteed to be nonzero (which is the "no ID" indicator). | 27 // The returned ID is guaranteed to be nonzero (which is the "no ID" indicator). |
22 static int GetUniqueIDInConstructor() { | 28 int GetUniqueIDInConstructor() { |
23 static int unique_id_counter = 0; | 29 static int unique_id_counter = 0; |
24 return ++unique_id_counter; | 30 return ++unique_id_counter; |
25 } | 31 } |
26 | 32 |
27 namespace content { | 33 void RecursivelyGenerateFrameEntries(const ExplodedFrameState& state, |
| 34 NavigationEntryImpl::TreeNode* node) { |
| 35 node->frame_entry = new FrameNavigationEntry( |
| 36 -1, UTF16ToUTF8(state.target.string()), state.item_sequence_number, |
| 37 state.document_sequence_number, nullptr, GURL(state.url_string.string()), |
| 38 Referrer(GURL(state.referrer.string()), state.referrer_policy)); |
| 39 |
| 40 // Set a single-frame PageState on the entry. |
| 41 ExplodedPageState page_state; |
| 42 page_state.top = state; |
| 43 std::string data; |
| 44 if (EncodePageState(page_state, &data)) |
| 45 node->frame_entry->set_page_state(PageState::CreateFromEncodedData(data)); |
| 46 |
| 47 for (const ExplodedFrameState& child_state : state.children) { |
| 48 NavigationEntryImpl::TreeNode* child_node = |
| 49 new NavigationEntryImpl::TreeNode(nullptr); |
| 50 node->children.push_back(child_node); |
| 51 RecursivelyGenerateFrameEntries(child_state, child_node); |
| 52 } |
| 53 } |
| 54 |
| 55 void RecursivelyGenerateFrameState( |
| 56 NavigationEntryImpl::TreeNode* node, |
| 57 ExplodedFrameState* state, |
| 58 std::vector<base::NullableString16>* referenced_files) { |
| 59 // The FrameNavigationEntry's PageState contains just the ExplodedFrameState |
| 60 // for that particular frame. |
| 61 ExplodedPageState exploded_page_state; |
| 62 if (!DecodePageState(node->frame_entry->page_state().ToEncodedData(), |
| 63 &exploded_page_state)) { |
| 64 NOTREACHED(); |
| 65 return; |
| 66 } |
| 67 ExplodedFrameState frame_state = exploded_page_state.top; |
| 68 |
| 69 // Copy the FrameNavigationEntry's frame state into the destination state. |
| 70 *state = frame_state; |
| 71 |
| 72 // Copy the frame's files into the PageState's |referenced_files|. |
| 73 referenced_files->reserve(referenced_files->size() + |
| 74 exploded_page_state.referenced_files.size()); |
| 75 for (auto& file : exploded_page_state.referenced_files) |
| 76 referenced_files->push_back(file); |
| 77 |
| 78 state->children.resize(node->children.size()); |
| 79 for (size_t i = 0; i < node->children.size(); ++i) { |
| 80 RecursivelyGenerateFrameState(node->children[i], &state->children[i], |
| 81 referenced_files); |
| 82 } |
| 83 } |
| 84 |
| 85 } // namespace |
28 | 86 |
29 int NavigationEntryImpl::kInvalidBindings = -1; | 87 int NavigationEntryImpl::kInvalidBindings = -1; |
30 | 88 |
31 NavigationEntryImpl::TreeNode::TreeNode(FrameNavigationEntry* frame_entry) | 89 NavigationEntryImpl::TreeNode::TreeNode(FrameNavigationEntry* frame_entry) |
32 : frame_entry(frame_entry) { | 90 : frame_entry(frame_entry) { |
33 } | 91 } |
34 | 92 |
35 NavigationEntryImpl::TreeNode::~TreeNode() { | 93 NavigationEntryImpl::TreeNode::~TreeNode() { |
36 } | 94 } |
37 | 95 |
(...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
173 void NavigationEntryImpl::SetTitle(const base::string16& title) { | 231 void NavigationEntryImpl::SetTitle(const base::string16& title) { |
174 title_ = title; | 232 title_ = title; |
175 cached_display_title_.clear(); | 233 cached_display_title_.clear(); |
176 } | 234 } |
177 | 235 |
178 const base::string16& NavigationEntryImpl::GetTitle() const { | 236 const base::string16& NavigationEntryImpl::GetTitle() const { |
179 return title_; | 237 return title_; |
180 } | 238 } |
181 | 239 |
182 void NavigationEntryImpl::SetPageState(const PageState& state) { | 240 void NavigationEntryImpl::SetPageState(const PageState& state) { |
183 frame_tree_->frame_entry->set_page_state(state); | 241 if (!SiteIsolationPolicy::UseSubframeNavigationEntries()) { |
| 242 frame_tree_->frame_entry->set_page_state(state); |
| 243 return; |
| 244 } |
184 | 245 |
185 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | 246 // This should only be called when restoring a NavigationEntry, so there |
186 // Also get the root ISN and DSN out of the PageState. | 247 // should be no subframe FrameNavigationEntries yet. |
187 ExplodedPageState exploded_state; | 248 DCHECK_EQ(0U, frame_tree_->children.size()); |
188 if (!DecodePageState(state.ToEncodedData(), &exploded_state)) | 249 |
189 return; | 250 // If the PageState can't be parsed or has no children, just store it on the |
190 frame_tree_->frame_entry->set_item_sequence_number( | 251 // main frame's FrameNavigationEntry without recursively creating subframe |
191 exploded_state.top.item_sequence_number); | 252 // entries. |
192 frame_tree_->frame_entry->set_document_sequence_number( | 253 ExplodedPageState exploded_state; |
193 exploded_state.top.document_sequence_number); | 254 if (!DecodePageState(state.ToEncodedData(), &exploded_state) || |
| 255 exploded_state.top.children.size() == 0U) { |
| 256 frame_tree_->frame_entry->set_page_state(state); |
| 257 return; |
194 } | 258 } |
| 259 |
| 260 RecursivelyGenerateFrameEntries(exploded_state.top, frame_tree_.get()); |
195 } | 261 } |
196 | 262 |
197 const PageState& NavigationEntryImpl::GetPageState() const { | 263 PageState NavigationEntryImpl::GetPageState() const { |
198 return frame_tree_->frame_entry->page_state(); | 264 // Just return the main frame's PageState in default Chrome, or if there are |
| 265 // no subframe FrameNavigationEntries. |
| 266 if (!SiteIsolationPolicy::UseSubframeNavigationEntries() || |
| 267 frame_tree_->children.size() == 0U) |
| 268 return frame_tree_->frame_entry->page_state(); |
| 269 |
| 270 // When we're using subframe entries, each FrameNavigationEntry has a |
| 271 // frame-specific PageState. We combine these into an ExplodedPageState tree |
| 272 // and generate a full PageState from it. |
| 273 ExplodedPageState exploded_state; |
| 274 RecursivelyGenerateFrameState(frame_tree_.get(), &exploded_state.top, |
| 275 &exploded_state.referenced_files); |
| 276 |
| 277 std::string encoded_data; |
| 278 if (!EncodePageState(exploded_state, &encoded_data)) |
| 279 return frame_tree_->frame_entry->page_state(); |
| 280 |
| 281 return PageState::CreateFromEncodedData(encoded_data); |
199 } | 282 } |
200 | 283 |
201 void NavigationEntryImpl::SetPageID(int page_id) { | 284 void NavigationEntryImpl::SetPageID(int page_id) { |
202 page_id_ = page_id; | 285 page_id_ = page_id; |
203 } | 286 } |
204 | 287 |
205 int32 NavigationEntryImpl::GetPageID() const { | 288 int32 NavigationEntryImpl::GetPageID() const { |
206 return page_id_; | 289 return page_id_; |
207 } | 290 } |
208 | 291 |
(...skipping 431 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
640 return node; | 723 return node; |
641 } | 724 } |
642 // Enqueue any children and keep looking. | 725 // Enqueue any children and keep looking. |
643 for (auto& child : node->children) | 726 for (auto& child : node->children) |
644 work_queue.push(child); | 727 work_queue.push(child); |
645 } | 728 } |
646 return nullptr; | 729 return nullptr; |
647 } | 730 } |
648 | 731 |
649 } // namespace content | 732 } // namespace content |
OLD | NEW |