Sigurdur Asgeirsson | 51d9d24 | 2019-10-07 20:38:34 | [diff] [blame] | 1 | # Performance Manager Overview |
| 2 | |
Sigurdur Asgeirsson | cdd10d6 | 2020-02-14 19:50:14 | [diff] [blame] | 3 | [TOC] |
Olivier Li | 0e6cff5 | 2020-02-04 17:51:21 | [diff] [blame] | 4 | |
Sigurdur Asgeirsson | cdd10d6 | 2020-02-14 19:50:14 | [diff] [blame] | 5 | # Overview |
Olivier Li | 0e6cff5 | 2020-02-04 17:51:21 | [diff] [blame] | 6 | |
Sigurdur Asgeirsson | cdd10d6 | 2020-02-14 19:50:14 | [diff] [blame] | 7 | The Performance Manager supports data-driven, centralized resource management, |
| 8 | prioritization and planning for the Chrome browser. Over time, data-driven, |
| 9 | centralized resource management will supplant and/or supplement the heuristics |
| 10 | that can be found all over Chrome at present. |
| 11 | |
| 12 | Here’s an overview picture of the intended architecture: |
| 13 | |
| 14 |  |
| 15 | |
| 16 | - The *Embedder* is responsible for notifying the |
| 17 | [Performance Manager Registry](embedder/performance_manager_registry.h) when |
| 18 | content entities are created or their relationships change. The Performance Manager |
| 19 | Registry maintains the structure of the Graph, which is a coarsely abstracted view of the state |
| 20 | of the browser. |
| 21 | - Decorators populate the graph nodes with interesting properties and data, such as e.g. the results |
| 22 | of CPU, memory and battery measurements and so on. |
| 23 | - Aggregators aggregate data in the graph, possibly across nodes. |
| 24 | As an example, the memory usage of all frame nodes could be summed up to their associated page |
| 25 | node, to establish the total memory usage of the page. |
| 26 | - Resource Management Policies are observers of the graph, and use the graph structure as well as |
| 27 | the properties of graph nodes to make policy decisions. |
| 28 | - Resource Management Mechanisms are invoked by Resource Management Policy to implement policy |
| 29 | decisions. |
| 30 | Note that while the mechanisms are depicted in the main thread, they can be hosted anywhere |
| 31 | necessary or convenient, such as in a renderer process at the far end of a mojo::Remote<>. |
| 32 | - Content Proxies are a convenience feature to allow easy and safe access from nodes in the graph |
| 33 | to the corresponding content entity for any task that needs to run on the main thread. |
| 34 | |
| 35 | The graph lives on the Performance Manager Sequence, as do all graph observers and mutators. |
| 36 | The graph structure can be viewed in the graph tab of the `chrome://discards WebUI.` |
| 37 | |
| 38 | In addition to the above, the Performance Manager also provides support for |
| 39 | users that need to occasionally query the graph to e.g. collect metrics. |
| 40 | |
| 41 | # Details |
| 42 | |
| 43 | ## Graph |
| 44 | |
| 45 | The performance manager exposes a simplified, coarse model of the browser’s |
| 46 | state as a [Graph](public/graph/graph.h) of [Nodes](public/graph/node.h), |
| 47 | where the nodes represent such things as: |
| 48 | 1. [Page](public/graph/page_node.h): corresponds to a content::WebContents. |
| 49 | 1. [Frame](public/graph/frame_node.h): corresponds to a frame in a |
| 50 | content::WebContents frame tree. |
| 51 | 1. [Process](public/graph/process_node.h): corresponds to a content::RenderProcessHost or |
| 52 | other type of process, such as e.g. the Browser or GPU process. |
| 53 | 1. [Worker](public/graph/worker_node.h): corresponds to a web worker. |
| 54 | |
| 55 | Nodes in the graph are connected with edges, such that e.g. each frame or worker |
| 56 | connects to its hosting process. |
| 57 | Frames are connected in a tree, and all frames in a tree connect to their |
| 58 | corresponding page. |
| 59 | Other edge types may denote dependencies between nodes, such as e.g. a |
| 60 | MessagePort connection or the like. Different node types in the graph are |
| 61 | adorned with different sets of properties, each of which represents necessary |
| 62 | information about the particular node type. |
| 63 | The graph provides node lookup and retrieval, as well as an observer interface |
| 64 | for notification of addition and removal of nodes, as well as node property |
| 65 | changes. |
| 66 | The graph also provides a way for users to adorn nodes with private data by means of |
| 67 | [Node Attached Data](public/graph/node_attached_data.h). |
| 68 | It’s preferable to store data that’s used for intermediate results or for |
| 69 | private purposes in Node Attached Data rather than in Node properties. |
| 70 | |
| 71 | ## Public & Private APIs. |
| 72 | |
| 73 | The graph exposes both a public and a private API. The private API is only |
| 74 | available to code in the component’s directory, whereas the public API can be |
| 75 | used by anyone in the browser process. The private API provides read-write |
| 76 | access to nodes and allows for node-intimate storage of node attached |
| 77 | properties. The public API provides read-only access to nodes, but otherwise the |
| 78 | two APIs are fairly similar. Where possible, using the public API is preferable, |
| 79 | as the public API is more stable, and doesn’t require the user to live in the |
| 80 | component. |
| 81 | |
| 82 | Good examples where the public API is appropriate, is e.g. for periodically |
| 83 | collecting metrics by iteration over the graph, or where iterating over the |
| 84 | graph can yield a set of content entities for some operation. As an example, |
| 85 | finding the set of frames in a page that belong to the same browsing instance |
| 86 | would be easy to do by iterating over the graph. |
| 87 | |
| 88 | ## Decorators |
| 89 | |
| 90 | Decorators set properties on the graph that are derived from data external to |
| 91 | the graph itself, such as e.g. performance measurement data. |
| 92 | |
| 93 | A simple example Decorator might periodically measure the cumulative CPU usage |
| 94 | for each process Node in the Graph and adorn each node with the measured |
| 95 | cumulative CPU usage of the corresponding process. |
| 96 | |
| 97 | ## Aggregators |
| 98 | |
| 99 | Aggregators, like Decorators, set properties on the graph nodes. The difference is that |
| 100 | Aggregators work solely on data in the graph, to e.g. aggregate or distribute data from |
| 101 | one node to another. |
| 102 | |
| 103 | A simple example Aggregator working with the simple example Decorator above might |
| 104 | compute the difference in cumulative CPU usage from the most recent measurement, |
| 105 | then distribute the difference across the Frame (and/or Worker) nodes associated |
| 106 | with each Process. |
| 107 | This would in turn allow summing up the cumulative CPU usage of each Frame and |
| 108 | Worker node to their associated Page node. This would yield the CPU usage of |
| 109 | the entire Page (content::WebContents). |
| 110 | |
| 111 | ## Policies & Mechanisms |
| 112 | |
| 113 | The intent is for all Resource Management Policies to use the graph and the data |
| 114 | therein to make policy decisions. The decisions are then implemented by invoking |
| 115 | some kind of Resource Management Mechanism. Making this a clean distinction |
| 116 | makes the implementation easier, more readable and more testable. |
| 117 | |
| 118 | A simple example of a policy and a mechanism might be a policy for flushing some |
| 119 | kind of a cache after all frames in a process have been backgrounded or idle for |
| 120 | a set amount of time. This policy would register for the appropriate |
| 121 | notifications and likely maintain private state on a process node. When the |
| 122 | criteria for flushing is met, the policy invokes the mechanism by rendezvousing |
| 123 | to a process-associated mojo interface and invoking on it. |
| 124 | |
| 125 | If the mojo interface is accessible through a content entity (e.g. |
| 126 | content::WebContents), the mechanism invocation is posted to the main thread |
| 127 | where the relevant content proxy (e.g. performance_manager::WebContentsProxy) |
| 128 | makes it easy and safe to retrieve the content entity on the main thread. |
| 129 | Should the corresponding content entity have been deleted after the task was |
| 130 | posted, the content proxy will simply return nullptr. |