blob: fdbb94f8bf724e1dc682f7978dddbb4aa81858f6 [file] [log] [blame]
Brandon Wymana0f33ce2019-10-17 18:32:29 -05001#pragma once
2
Brandon Wyman8d195772020-01-27 15:03:51 -06003#include "pmbus.hpp"
Brandon Wymanaed1f752019-11-25 18:10:52 -06004#include "types.hpp"
Brandon Wyman3f1242f2020-01-28 13:11:25 -06005#include "utility.hpp"
Brandon Wymanaed1f752019-11-25 18:10:52 -06006
7#include <sdbusplus/bus/match.hpp>
8
Brandon Wymana0f33ce2019-10-17 18:32:29 -05009namespace phosphor::power::psu
10{
Brandon Wyman3f1242f2020-01-28 13:11:25 -060011
Brandon Wymana0f33ce2019-10-17 18:32:29 -050012/**
13 * @class PowerSupply
14 * Represents a PMBus power supply device.
15 */
16class PowerSupply
17{
18 public:
Brandon Wymanaed1f752019-11-25 18:10:52 -060019 PowerSupply() = delete;
Brandon Wymana0f33ce2019-10-17 18:32:29 -050020 PowerSupply(const PowerSupply&) = delete;
21 PowerSupply(PowerSupply&&) = delete;
22 PowerSupply& operator=(const PowerSupply&) = delete;
23 PowerSupply& operator=(PowerSupply&&) = delete;
24 ~PowerSupply() = default;
25
26 /**
Brandon Wymanc63941c2020-01-27 16:49:33 -060027 * @param[in] invpath - String for inventory path to use
28 * @param[in] i2cbus - The bus number this power supply is on
29 * @param[in] i2caddr - The 16-bit I2C address of the power supply
Brandon Wymanaed1f752019-11-25 18:10:52 -060030 */
Brandon Wymanc63941c2020-01-27 16:49:33 -060031 PowerSupply(sdbusplus::bus::bus& bus, const std::string& invpath,
32 std::uint8_t i2cbus, const std::string& i2caddr) :
33 bus(bus),
Brandon Wyman8d195772020-01-27 15:03:51 -060034 inventoryPath(invpath),
35 pmbusIntf(phosphor::pmbus::createPMBus(i2cbus, i2caddr))
Brandon Wymanaed1f752019-11-25 18:10:52 -060036 {
37 // Setup the functions to call when the D-Bus inventory path for the
38 // Present property changes.
39 presentMatch = std::make_unique<sdbusplus::bus::match_t>(
40 bus,
41 sdbusplus::bus::match::rules::propertiesChanged(inventoryPath,
42 INVENTORY_IFACE),
43 [this](auto& msg) { this->inventoryChanged(msg); });
44 presentAddedMatch = std::make_unique<sdbusplus::bus::match_t>(
45 bus,
46 sdbusplus::bus::match::rules::interfacesAdded() +
47 sdbusplus::bus::match::rules::path_namespace(inventoryPath),
48 [this](auto& msg) { this->inventoryChanged(msg); });
49 // Get the current state of the Present property.
50 updatePresence();
51 }
52
Brandon Wyman3f1242f2020-01-28 13:11:25 -060053 phosphor::pmbus::PMBusBase& getPMBus()
54 {
55 return *pmbusIntf;
56 }
57
Brandon Wymanaed1f752019-11-25 18:10:52 -060058 /**
Brandon Wymana0f33ce2019-10-17 18:32:29 -050059 * Power supply specific function to analyze for faults/errors.
60 *
61 * Various PMBus status bits will be checked for fault conditions.
62 * If a certain fault bits are on, the appropriate error will be
63 * committed.
64 */
Brandon Wyman3f1242f2020-01-28 13:11:25 -060065 void analyze();
Brandon Wymana0f33ce2019-10-17 18:32:29 -050066
67 /**
68 * Write PMBus CLEAR_FAULTS
69 *
70 * This function will be called in various situations in order to clear
71 * any fault status bits that may have been set, in order to start over
72 * with a clean state. Presence changes and power state changes will
73 * want to clear any faults logged.
74 */
75 void clearFaults()
76 {
Brandon Wyman3f1242f2020-01-28 13:11:25 -060077 faultFound = false;
78 inputFault = false;
79 mfrFault = false;
80 vinUVFault = false;
Brandon Wyman4e016652020-04-28 19:31:17 -050081
82 // The PMBus device driver does not allow for writing CLEAR_FAULTS
83 // directly. However, the pmbus hwmon device driver code will send a
84 // CLEAR_FAULTS after reading from any of the hwmon "files" in sysfs, so
85 // reading in1_crit should result in clearing the fault bits in
86 // STATUS_BYTE/STATUS_WORD.
87 // I do not care what the return value is.
88 static_cast<void>(
89 pmbusIntf->read("in1_crit", phosphor::pmbus::Type::Hwmon));
Brandon Wymana0f33ce2019-10-17 18:32:29 -050090 }
91
92 /**
93 * @brief Adds properties to the inventory.
94 *
95 * Reads the values from the device and writes them to the
96 * associated power supply D-Bus inventory object.
97 *
98 * This needs to be done on startup, and each time the presence
99 * state changes.
100 *
101 * Properties added:
102 * - Serial Number
103 * - Part Number
104 * - CCIN (Customer Card Identification Number) - added as the Model
105 * - Firmware version
106 */
107 void updateInventory()
108 {
109 }
110
Brandon Wymanaed1f752019-11-25 18:10:52 -0600111 /**
112 * @brief Accessor function to indicate present status
113 */
114 bool isPresent() const
115 {
116 return present;
117 }
118
Brandon Wyman3f1242f2020-01-28 13:11:25 -0600119 /**
120 * @brief Returns true if a fault was found.
121 */
122 bool isFaulted() const
123 {
124 return faultFound;
125 }
126
127 /**
128 * @brief Returns true if INPUT fault occurred.
129 */
130 bool hasInputFault() const
131 {
132 return inputFault;
133 }
134
135 /**
136 * @brief Returns true if MFRSPECIFIC occurred.
137 */
138 bool hasMFRFault() const
139 {
140 return mfrFault;
141 }
142
143 /**
144 * @brief Returns true if VIN_UV_FAULT occurred.
145 */
146 bool hasVINUVFault() const
147 {
148 return vinUVFault;
149 }
150
Brandon Wymana0f33ce2019-10-17 18:32:29 -0500151 private:
Brandon Wymanaed1f752019-11-25 18:10:52 -0600152 /** @brief systemd bus member */
153 sdbusplus::bus::bus& bus;
154
Brandon Wymana0f33ce2019-10-17 18:32:29 -0500155 /** @brief True if a fault has already been found and not cleared */
156 bool faultFound = false;
Brandon Wymanaed1f752019-11-25 18:10:52 -0600157
Brandon Wyman3f1242f2020-01-28 13:11:25 -0600158 /** @brief True if bit 5 of STATUS_WORD high byte is on. */
159 bool inputFault = false;
160
161 /** @brief True if bit 4 of STATUS_WORD high byte is on. */
162 bool mfrFault = false;
163
164 /** @brief True if bit 3 of STATUS_WORD low byte is on. */
165 bool vinUVFault = false;
166
Brandon Wymanaed1f752019-11-25 18:10:52 -0600167 /**
168 * @brief D-Bus path to use for this power supply's inventory status.
169 **/
170 std::string inventoryPath;
171
172 /** @brief True if the power supply is present. */
173 bool present = false;
174
175 /** @brief D-Bus match variable used to subscribe to Present property
176 * changes.
177 **/
178 std::unique_ptr<sdbusplus::bus::match_t> presentMatch;
179
180 /** @brief D-Bus match variable used to subscribe for Present property
181 * interface added.
182 */
183 std::unique_ptr<sdbusplus::bus::match_t> presentAddedMatch;
184
185 /**
Brandon Wyman8d195772020-01-27 15:03:51 -0600186 * @brief Pointer to the PMBus interface
187 *
188 * Used to read or write to/from PMBus power supply devices.
189 */
190 std::unique_ptr<phosphor::pmbus::PMBusBase> pmbusIntf;
191
192 /**
Brandon Wymanaed1f752019-11-25 18:10:52 -0600193 * @brief Updates the presence status by querying D-Bus
194 *
195 * The D-Bus inventory properties for this power supply will be read to
196 * determine if the power supply is present or not and update this
197 * object's present member variable to reflect current status.
198 **/
199 void updatePresence();
200
201 /**
202 * @brief Callback for inventory property changes
203 *
204 * Process change of Present property for power supply.
205 *
206 * @param[in] msg - Data associated with Present change signal
207 **/
208 void inventoryChanged(sdbusplus::message::message& msg);
Brandon Wymana0f33ce2019-10-17 18:32:29 -0500209};
210
211} // namespace phosphor::power::psu