Commit 25852494 authored by Patrick Monette's avatar Patrick Monette Committed by Commit Bot

[PM] Migrate BoostingVoteAggregator to VoteObserver

Bug: 971272
Change-Id: I56b43e5119db30fae638be3503a2c990241e5430
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2530215
Commit-Queue: Patrick Monette <pmonette@chromium.org>
Reviewed-by: default avatarChris Hamilton <chrisha@chromium.org>
Cr-Commit-Position: refs/heads/master@{#828080}
parent abbc3d08
...@@ -189,15 +189,6 @@ void BoostingVoteAggregator::NodeData::DecrementEdgeCount() { ...@@ -189,15 +189,6 @@ void BoostingVoteAggregator::NodeData::DecrementEdgeCount() {
--edge_count_; --edge_count_;
} }
VoteReceipt BoostingVoteAggregator::NodeData::SetIncomingVote(
VoteConsumer* consumer,
voting::VoterId<Vote> voter_id,
const ExecutionContext* execution_context,
const Vote& vote) {
incoming_ = AcceptedVote(consumer, voter_id, execution_context, vote);
return incoming_.IssueReceipt();
}
BoostingVoteAggregator::EdgeData::EdgeData() = default; BoostingVoteAggregator::EdgeData::EdgeData() = default;
BoostingVoteAggregator::EdgeData::EdgeData(EdgeData&&) = default; BoostingVoteAggregator::EdgeData::EdgeData(EdgeData&&) = default;
...@@ -247,7 +238,8 @@ const char* BoostingVoteAggregator::EdgeData::GetActiveReason() const { ...@@ -247,7 +238,8 @@ const char* BoostingVoteAggregator::EdgeData::GetActiveReason() const {
return reasons_[0]; return reasons_[0];
} }
BoostingVoteAggregator::BoostingVoteAggregator() : factory_(this) {} BoostingVoteAggregator::BoostingVoteAggregator()
: vote_consumer_default_impl_(this) {}
BoostingVoteAggregator::~BoostingVoteAggregator() { BoostingVoteAggregator::~BoostingVoteAggregator() {
DCHECK(forward_edges_.empty()); DCHECK(forward_edges_.empty());
...@@ -257,8 +249,8 @@ BoostingVoteAggregator::~BoostingVoteAggregator() { ...@@ -257,8 +249,8 @@ BoostingVoteAggregator::~BoostingVoteAggregator() {
VotingChannel BoostingVoteAggregator::GetVotingChannel() { VotingChannel BoostingVoteAggregator::GetVotingChannel() {
DCHECK(nodes_.empty()); DCHECK(nodes_.empty());
DCHECK_EQ(voting::kInvalidVoterId<Vote>, input_voter_id_); DCHECK_EQ(voting::kInvalidVoterId<Vote>, input_voter_id_);
DCHECK_GT(1u, factory_.voting_channels_issued()); DCHECK_GT(1u, vote_consumer_default_impl_.voting_channels_issued());
auto channel = factory_.BuildVotingChannel(); auto channel = vote_consumer_default_impl_.BuildVotingChannel();
input_voter_id_ = channel.voter_id(); input_voter_id_ = channel.voter_id();
return channel; return channel;
} }
...@@ -395,19 +387,16 @@ void BoostingVoteAggregator::CancelBoostingVote( ...@@ -395,19 +387,16 @@ void BoostingVoteAggregator::CancelBoostingVote(
} }
} }
VoteReceipt BoostingVoteAggregator::SubmitVote( void BoostingVoteAggregator::OnVoteSubmitted(
util::PassKey<VotingChannel>, VoterId voter_id,
voting::VoterId<Vote> voter_id,
const ExecutionContext* execution_context, const ExecutionContext* execution_context,
const Vote& vote) { const Vote& vote) {
DCHECK(IsSetup()); DCHECK(IsSetup());
DCHECK_EQ(input_voter_id_, voter_id); DCHECK_EQ(input_voter_id_, voter_id);
DCHECK(vote.IsValid());
// Store the vote. // Store the vote.
auto node_data_it = FindOrCreateNodeData(execution_context); auto node_data_it = FindOrCreateNodeData(execution_context);
VoteReceipt receipt = node_data_it->second.SetIncomingVote( node_data_it->second.SetIncomingVote(vote);
this, voter_id, execution_context, vote);
NodeDataPtrSet changes; NodeDataPtrSet changes;
...@@ -418,21 +407,21 @@ VoteReceipt BoostingVoteAggregator::SubmitVote( ...@@ -418,21 +407,21 @@ VoteReceipt BoostingVoteAggregator::SubmitVote(
} }
UpstreamChanges(changes); UpstreamChanges(changes);
return receipt;
} }
void BoostingVoteAggregator::ChangeVote(util::PassKey<AcceptedVote>, void BoostingVoteAggregator::OnVoteChanged(
AcceptedVote* old_vote, VoterId voter_id,
const Vote& new_vote) { const ExecutionContext* execution_context,
const Vote& new_vote) {
auto node_data_it = FindNodeData(execution_context);
auto* node_data = &(*node_data_it);
// Remember the old and new priorities before committing any changes. // Remember the old and new priorities before committing any changes.
base::TaskPriority old_priority = old_vote->vote().value(); base::TaskPriority old_priority = node_data->second.incoming_vote().value();
base::TaskPriority new_priority = new_vote.value(); base::TaskPriority new_priority = new_vote.value();
// Update the vote in place. // Update the vote in place.
auto node_data_it = GetNodeDataByVote(old_vote); node_data->second.UpdateIncomingVote(new_vote);
auto* node_data = &(*node_data_it);
old_vote->UpdateVote(new_vote);
NodeDataPtrSet changes; NodeDataPtrSet changes;
changes.insert(node_data); // This node is changing regardless. changes.insert(node_data); // This node is changing regardless.
...@@ -452,10 +441,17 @@ void BoostingVoteAggregator::ChangeVote(util::PassKey<AcceptedVote>, ...@@ -452,10 +441,17 @@ void BoostingVoteAggregator::ChangeVote(util::PassKey<AcceptedVote>,
UpstreamChanges(changes); UpstreamChanges(changes);
} }
void BoostingVoteAggregator::VoteInvalidated(util::PassKey<AcceptedVote>, void BoostingVoteAggregator::OnVoteInvalidated(
AcceptedVote* vote) { VoterId voter_id,
auto node_data_it = GetNodeDataByVote(vote); const ExecutionContext* execution_context) {
base::TaskPriority old_priority = vote->vote().value(); auto node_data_it = FindNodeData(execution_context);
// Remember the old priority before committing any changes.
base::TaskPriority old_priority =
node_data_it->second.incoming_vote().value();
// Update the vote.
node_data_it->second.RemoveIncomingVote();
NodeDataPtrSet changes; NodeDataPtrSet changes;
...@@ -498,21 +494,6 @@ void BoostingVoteAggregator::ForEachOutgoingEdge(const ExecutionContext* node, ...@@ -498,21 +494,6 @@ void BoostingVoteAggregator::ForEachOutgoingEdge(const ExecutionContext* node,
} }
} }
BoostingVoteAggregator::NodeDataMap::iterator
BoostingVoteAggregator::GetNodeDataByVote(AcceptedVote* vote) {
// The vote being retrieved should have us as its consumer, and have been
// emitted by our known voter.
DCHECK(vote);
DCHECK_EQ(this, vote->consumer());
DCHECK(vote->voter_id() == input_voter_id_);
DCHECK(IsSetup());
auto it = nodes_.find(vote->context());
DCHECK(it != nodes_.end());
DCHECK_EQ(vote, &it->second.incoming());
return it;
}
BoostingVoteAggregator::NodeDataMap::iterator BoostingVoteAggregator::NodeDataMap::iterator
BoostingVoteAggregator::FindOrCreateNodeData(const ExecutionContext* node) { BoostingVoteAggregator::FindOrCreateNodeData(const ExecutionContext* node) {
auto it = nodes_.lower_bound(node); auto it = nodes_.lower_bound(node);
...@@ -524,7 +505,7 @@ BoostingVoteAggregator::FindOrCreateNodeData(const ExecutionContext* node) { ...@@ -524,7 +505,7 @@ BoostingVoteAggregator::FindOrCreateNodeData(const ExecutionContext* node) {
BoostingVoteAggregator::NodeDataMap::iterator BoostingVoteAggregator::NodeDataMap::iterator
BoostingVoteAggregator::FindNodeData(const ExecutionContext* node) { BoostingVoteAggregator::FindNodeData(const ExecutionContext* node) {
auto it = nodes_.lower_bound(node); auto it = nodes_.find(node);
DCHECK(it != nodes_.end()); DCHECK(it != nodes_.end());
return it; return it;
} }
...@@ -542,11 +523,11 @@ const char* BoostingVoteAggregator::GetVoteReason( ...@@ -542,11 +523,11 @@ const char* BoostingVoteAggregator::GetVoteReason(
// If a vote has been expressed for this node at the given priority level then // If a vote has been expressed for this node at the given priority level then
// preferentially use that reason. // preferentially use that reason.
if (node_data.HasIncomingVote()) { if (node_data.HasIncomingVote()) {
const Vote& incoming = node_data.incoming().vote(); const Vote& incoming_vote = node_data.incoming_vote();
if (priority == incoming.value()) { if (priority == incoming_vote.value()) {
// This node will not have an active incoming edge in this case. // This node will not have an active incoming edge in this case.
DCHECK(GetActiveInboundEdge(layer_bit, node) == reverse_edges_.end()); DCHECK(GetActiveInboundEdge(layer_bit, node) == reverse_edges_.end());
return incoming.reason(); return incoming_vote.reason();
} }
} }
......
...@@ -9,6 +9,7 @@ ...@@ -9,6 +9,7 @@
#include <set> #include <set>
#include "base/containers/flat_map.h" #include "base/containers/flat_map.h"
#include "base/optional.h"
#include "base/task/task_traits.h" #include "base/task/task_traits.h"
#include "components/performance_manager/public/execution_context_priority/execution_context_priority.h" #include "components/performance_manager/public/execution_context_priority/execution_context_priority.h"
...@@ -69,7 +70,7 @@ class BoostingVote { ...@@ -69,7 +70,7 @@ class BoostingVote {
// execution context Y". It is intended to serve as the root of a tree of voters // execution context Y". It is intended to serve as the root of a tree of voters
// and aggregators, allowing priority boost semantics to be implemented. This // and aggregators, allowing priority boost semantics to be implemented. This
// class must outlive all boosting votes registered with it. // class must outlive all boosting votes registered with it.
class BoostingVoteAggregator : public VoteConsumer { class BoostingVoteAggregator : public VoteObserver {
public: public:
BoostingVoteAggregator(); BoostingVoteAggregator();
~BoostingVoteAggregator() override; ~BoostingVoteAggregator() override;
...@@ -126,15 +127,21 @@ class BoostingVoteAggregator : public VoteConsumer { ...@@ -126,15 +127,21 @@ class BoostingVoteAggregator : public VoteConsumer {
NodeData& operator=(NodeData&& rhs) = default; NodeData& operator=(NodeData&& rhs) = default;
~NodeData(); ~NodeData();
const AcceptedVote& incoming() const { return incoming_; } const Vote& incoming_vote() const { return incoming_vote_.value(); }
const VoteReceipt& receipt() const { return receipt_; } const VoteReceipt& receipt() const { return receipt_; }
// For modifying |incoming_|. void SetIncomingVote(const Vote& incoming_vote) {
VoteReceipt SetIncomingVote(VoteConsumer* consumer, DCHECK(!incoming_vote_.has_value());
voting::VoterId<Vote> voter_id, incoming_vote_ = incoming_vote;
const ExecutionContext* execution_context, }
const Vote& vote); void UpdateIncomingVote(const Vote& incoming_vote) {
void UpdateIncomingVote(const Vote& vote) { incoming_.UpdateVote(vote); } DCHECK(incoming_vote_.has_value());
incoming_vote_ = incoming_vote;
}
void RemoveIncomingVote() {
DCHECK(incoming_vote_.has_value());
incoming_vote_ = base::nullopt;
}
// For modifying |receipt_|. // For modifying |receipt_|.
void ChangeOutgoingVote(base::TaskPriority priority, const char* reason) { void ChangeOutgoingVote(base::TaskPriority priority, const char* reason) {
...@@ -147,10 +154,10 @@ class BoostingVoteAggregator : public VoteConsumer { ...@@ -147,10 +154,10 @@ class BoostingVoteAggregator : public VoteConsumer {
// Returns true if this node has an active |incoming| vote. If false that // Returns true if this node has an active |incoming| vote. If false that
// means this node exists only because it is referenced by a BoostedVote. // means this node exists only because it is referenced by a BoostedVote.
// Same as |incoming_.IsValid()|, but more readable. // Same as |incoming_vote_.has_value()|, but more readable.
bool HasIncomingVote() const { return incoming_.IsValid(); } bool HasIncomingVote() const { return incoming_vote_.has_value(); }
// Returns true if this node has an active outgoing vote. Sam as // Returns true if this node has an active outgoing vote. Same as
// |receipt_.HasVote()|, but more readable. // |receipt_.HasVote()|, but more readable.
bool HasOutgoingVote() const { return receipt_.HasVote(); } bool HasOutgoingVote() const { return receipt_.HasVote(); }
...@@ -174,7 +181,7 @@ class BoostingVoteAggregator : public VoteConsumer { ...@@ -174,7 +181,7 @@ class BoostingVoteAggregator : public VoteConsumer {
size_t edge_count_ = 0; size_t edge_count_ = 0;
// The input vote we've received, if any. // The input vote we've received, if any.
AcceptedVote incoming_; base::Optional<Vote> incoming_vote_;
// The receipt for the vote we've upstreamed, if any. // The receipt for the vote we've upstreamed, if any.
VoteReceipt receipt_; VoteReceipt receipt_;
...@@ -267,16 +274,15 @@ class BoostingVoteAggregator : public VoteConsumer { ...@@ -267,16 +274,15 @@ class BoostingVoteAggregator : public VoteConsumer {
void SubmitBoostingVote(const BoostingVote* boosting_vote); void SubmitBoostingVote(const BoostingVote* boosting_vote);
void CancelBoostingVote(const BoostingVote* boosting_vote); void CancelBoostingVote(const BoostingVote* boosting_vote);
// VoteConsumer implementation: // VoteObserver implementation:
VoteReceipt SubmitVote(util::PassKey<VotingChannel>, void OnVoteSubmitted(VoterId voter_id,
voting::VoterId<Vote> voter_id, const ExecutionContext* execution_context,
const ExecutionContext* execution_context, const Vote& vote) override;
const Vote& vote) override; void OnVoteChanged(VoterId voter_id,
void ChangeVote(util::PassKey<AcceptedVote>, const ExecutionContext* execution_context,
AcceptedVote* old_vote, const Vote& new_vote) override;
const Vote& new_vote) override; void OnVoteInvalidated(VoterId voter_id,
void VoteInvalidated(util::PassKey<AcceptedVote>, const ExecutionContext* execution_context) override;
AcceptedVote* vote) override;
// Helper functions for enumerating over incoming and outgoing edges. // Helper functions for enumerating over incoming and outgoing edges.
// |function| should accept a single input parameter that is a // |function| should accept a single input parameter that is a
...@@ -288,10 +294,6 @@ class BoostingVoteAggregator : public VoteConsumer { ...@@ -288,10 +294,6 @@ class BoostingVoteAggregator : public VoteConsumer {
template <typename Function> template <typename Function>
void ForEachOutgoingEdge(const ExecutionContext* node, Function&& function); void ForEachOutgoingEdge(const ExecutionContext* node, Function&& function);
// Looks up the NodeData associated with the provided |vote|. The data is
// expected to already exist (enforced by a DCHECK).
NodeDataMap::iterator GetNodeDataByVote(AcceptedVote* vote);
// Finds or creates the node data associated with the given node. // Finds or creates the node data associated with the given node.
NodeDataMap::iterator FindOrCreateNodeData(const ExecutionContext* node); NodeDataMap::iterator FindOrCreateNodeData(const ExecutionContext* node);
NodeDataMap::iterator FindNodeData(const ExecutionContext* node); NodeDataMap::iterator FindNodeData(const ExecutionContext* node);
...@@ -371,8 +373,8 @@ class BoostingVoteAggregator : public VoteConsumer { ...@@ -371,8 +373,8 @@ class BoostingVoteAggregator : public VoteConsumer {
// Our channel for upstreaming our votes. // Our channel for upstreaming our votes.
VotingChannel channel_; VotingChannel channel_;
// Our VotingChannelFactory for providing a VotingChannel to our input voter. // Provides a VotingChannel to our input voter.
VotingChannelFactory factory_; VoteConsumerDefaultImpl vote_consumer_default_impl_;
// Nodes and associated metadata in the "priority flow graph". An entry exists // Nodes and associated metadata in the "priority flow graph". An entry exists
// in this map for any node that has an active non-default vote, or for any // in this map for any node that has an active non-default vote, or for any
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment