PID Objects & Algo
These are the PID controller implementations for fans,
and thermals. This also includes the PID algorithm used.
Change-Id: I30471fbf7a8a7ed65f78bf105970d62815fedc56
Signed-off-by: Patrick Venture <venture@google.com>
diff --git a/pid/zone.hpp b/pid/zone.hpp
new file mode 100644
index 0000000..d75bf59
--- /dev/null
+++ b/pid/zone.hpp
@@ -0,0 +1,124 @@
+#pragma once
+
+#include <fstream>
+#include <map>
+#include <memory>
+#include <set>
+#include <string>
+#include <vector>
+
+#include "conf.hpp"
+#include "controller.hpp"
+#include "sensors/sensor.hpp"
+#include "sensors/manager.hpp"
+
+#include "xyz/openbmc_project/Control/FanCtrl/Mode/server.hpp"
+#include <sdbusplus/bus.hpp>
+#include <sdbusplus/server.hpp>
+
+
+template <typename... T>
+using ServerObject = typename sdbusplus::server::object::object<T...>;
+using ModeInterface =
+ sdbusplus::xyz::openbmc_project::Control::FanCtrl::server::Mode;
+using ModeObject = ServerObject<ModeInterface>;
+
+/*
+ * The PIDZone inherits from the Mode object so that it can listen for control
+ * mode changes. It primarily holds all PID loops and holds the sensor value
+ * cache that's used per iteration of the PID loops.
+ */
+class PIDZone : public ModeObject
+{
+ public:
+ PIDZone(int64_t zone,
+ float minThermalRpm,
+ float failSafePercent,
+ std::shared_ptr<SensorManager> mgr,
+ sdbusplus::bus::bus& bus,
+ const char* objPath,
+ bool defer)
+ : ModeObject(bus, objPath, defer),
+ _zoneId(zone),
+ _maximumRPMSetPt(),
+ _minThermalRpmSetPt(minThermalRpm),
+ _failSafePercent(failSafePercent),
+ _mgr(mgr)
+ {
+#ifdef __TUNING_LOGGING__
+ _log.open("/tmp/swampd.log");
+#endif
+ }
+
+ float getMaxRPMRequest(void) const;
+ bool getManualMode(void) const;
+
+ /* Could put lock around this since it's accessed from two threads, but
+ * only one reader/one writer.
+ */
+ void setManualMode(bool mode);
+ bool getFailSafeMode(void) const;
+ int64_t getZoneId(void) const;
+ void addRPMSetPoint(float setpoint);
+ void clearRPMSetPoints(void);
+ float getFailSafePercent(void) const;
+ float getMinThermalRpmSetPt(void) const;
+
+ std::unique_ptr<Sensor>& getSensor(std::string name);
+ void determineMaxRPMRequest(void);
+ void updateFanTelemetry(void);
+ void updateSensors(void);
+ void initializeCache(void);
+ void dumpCache(void);
+ void process_fans(void);
+ void process_thermals(void);
+
+ void addFanPID(std::unique_ptr<PIDController> pid);
+ void addThermalPID(std::unique_ptr<PIDController> pid);
+ double getCachedValue(const std::string& name);
+ void addFanInput(std::string fan);
+ void addThermalInput(std::string therm);
+
+#ifdef __TUNING_LOGGING__
+ void initializeLog(void);
+ std::ofstream& getLogHandle(void);
+#endif
+
+ /* Method for setting the manual mode over dbus */
+ bool manual(bool value) override;
+ /* Method for reading whether in fail-safe mode over dbus */
+ bool failSafe() const override;
+
+ private:
+#ifdef __TUNING_LOGGING__
+ std::ofstream _log;
+#endif
+
+ const int64_t _zoneId;
+ float _maximumRPMSetPt = 0;
+ bool _manualMode = false;
+ const float _minThermalRpmSetPt;
+ const float _failSafePercent;
+
+ std::set<std::string> _failSafeSensors;
+
+ std::vector<float> _RPMSetPoints;
+ std::vector<std::string> _fanInputs;
+ std::vector<std::string> _thermalInputs;
+ std::map<std::string, double> _cachedValuesByName;
+ std::shared_ptr<SensorManager> _mgr;
+
+ std::vector<std::unique_ptr<PIDController>> _fans;
+ std::vector<std::unique_ptr<PIDController>> _thermals;
+};
+
+std::map<int64_t, std::shared_ptr<PIDZone>> BuildZones(
+ std::map<int64_t, PIDConf>& ZonePids,
+ std::map<int64_t, struct zone>& ZoneConfigs,
+ std::shared_ptr<SensorManager> mgmr,
+ sdbusplus::bus::bus& ModeControlBus);
+
+std::map<int64_t, std::shared_ptr<PIDZone>> BuildZonesFromConfig(
+ std::string& path,
+ std::shared_ptr<SensorManager> mgmr,
+ sdbusplus::bus::bus& ModeControlBus);