Skip to main content

driver_manager_core/
offer_injection.rs

1// Copyright 2026 The Fuchsia 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
5use fidl_fuchsia_component_decl as fdecl;
6
7#[derive(Clone, Copy)]
8pub struct PowerOffersConfig {
9    pub power_inject_offer: bool,
10    pub power_suspend_enabled: bool,
11}
12
13#[derive(Clone)]
14pub struct OfferInjector {
15    power_config: PowerOffersConfig,
16}
17
18impl OfferInjector {
19    pub fn new(power_config: PowerOffersConfig) -> Self {
20        Self { power_config }
21    }
22
23    pub fn extra_offers_count(&self) -> usize {
24        let mut res = 0;
25        if self.power_config.power_inject_offer {
26            // 1 for the broker, 2 for the SAG.
27            res += 3;
28        }
29        res
30    }
31
32    pub fn inject(&self, dynamic_offers: &mut [fdecl::Offer], start_index: usize) {
33        let (sag_source, sag_availability) = if self.power_config.power_suspend_enabled {
34            (
35                fdecl::Ref::Child(fdecl::ChildRef {
36                    name: "system-activity-governor".to_string(),
37                    collection: None,
38                }),
39                fdecl::Availability::Required,
40            )
41        } else {
42            (fdecl::Ref::VoidType(fdecl::VoidRef {}), fdecl::Availability::Optional)
43        };
44
45        let (broker_source, broker_availability) = if self.power_config.power_suspend_enabled {
46            (
47                fdecl::Ref::Child(fdecl::ChildRef {
48                    name: "power-broker".to_string(),
49                    collection: None,
50                }),
51                fdecl::Availability::Required,
52            )
53        } else {
54            (fdecl::Ref::VoidType(fdecl::VoidRef {}), fdecl::Availability::Optional)
55        };
56
57        let mut offset = 0;
58
59        if self.power_config.power_inject_offer {
60            dynamic_offers[start_index + offset] = fdecl::Offer::Protocol(fdecl::OfferProtocol {
61                source: Some(sag_source.clone()),
62                source_name: Some("fuchsia.power.system.ActivityGovernor".to_string()),
63                target_name: Some("fuchsia.power.system.ActivityGovernor".to_string()),
64                dependency_type: Some(fdecl::DependencyType::Weak),
65                availability: Some(sag_availability),
66                ..Default::default()
67            });
68            offset += 1;
69
70            dynamic_offers[start_index + offset] = fdecl::Offer::Protocol(fdecl::OfferProtocol {
71                source: Some(sag_source),
72                source_name: Some("fuchsia.power.system.CpuElementManager".to_string()),
73                target_name: Some("fuchsia.power.system.CpuElementManager".to_string()),
74                dependency_type: Some(fdecl::DependencyType::Weak),
75                availability: Some(sag_availability),
76                ..Default::default()
77            });
78            offset += 1;
79
80            dynamic_offers[start_index + offset] = fdecl::Offer::Protocol(fdecl::OfferProtocol {
81                source: Some(broker_source),
82                source_name: Some("fuchsia.power.broker.Topology".to_string()),
83                target_name: Some("fuchsia.power.broker.Topology".to_string()),
84                dependency_type: Some(fdecl::DependencyType::Weak),
85                availability: Some(broker_availability),
86                ..Default::default()
87            });
88        }
89    }
90}