ESPHome 2025.5.0
Loading...
Searching...
No Matches
max9611.cpp
Go to the documentation of this file.
1#include "max9611.h"
2#include "esphome/core/log.h"
4namespace esphome {
5namespace max9611 {
6using namespace esphome::i2c;
7// Sign extend
8// http://graphics.stanford.edu/~seander/bithacks.html#FixedSignExtend
9template<typename T, unsigned B> inline T signextend(const T x) {
10 struct {
11 T x : B;
12 } s;
13 return s.x = x;
14}
15// Map the gain register to in uV/LSB
17 float lsb = 0.0;
19 lsb = 107.50;
20 } else if (gain == MAX9611_MULTIPLEXER_CSA_GAIN4) {
21 lsb = 26.88;
22 } else if (gain == MAX9611_MULTIPLEXER_CSA_GAIN8) {
23 lsb = 13.44;
24 }
25 return lsb;
26}
27static const char *const TAG = "max9611";
28static const uint8_t SETUP_DELAY = 4; // Wait 2 integration periods.
29static const float VOUT_LSB = 14.0 / 1000.0; // 14mV/LSB
30static const float TEMP_LSB = 0.48; // 0.48C/LSB
31static const float MICRO_VOLTS_PER_VOLT = 1000000.0;
33 ESP_LOGCONFIG(TAG, "Setting up max9611...");
34 // Perform dummy-read
35 uint8_t value;
36 this->read(&value, 1);
37 // Configuration Stage.
38 // First send an integration request with the specified gain
39 const uint8_t setup_dat[] = {CONTROL_REGISTER_1_ADRR, static_cast<uint8_t>(gain_)};
40 // Then send a request that samples all channels as fast as possible, using the last provided gain
42
43 if (this->write(reinterpret_cast<const uint8_t *>(&setup_dat), sizeof(setup_dat)) != ErrorCode::ERROR_OK) {
44 ESP_LOGE(TAG, "Failed to setup Max9611 during GAIN SET");
45 return;
46 }
47 delay(SETUP_DELAY);
48 if (this->write(reinterpret_cast<const uint8_t *>(&fast_mode_dat), sizeof(fast_mode_dat)) != ErrorCode::ERROR_OK) {
49 ESP_LOGE(TAG, "Failed to setup Max9611 during FAST MODE SET");
50 return;
51 }
52}
54 ESP_LOGCONFIG(TAG, "Dump Config max9611...");
55 ESP_LOGCONFIG(TAG, " CSA Gain Register: %x", gain_);
56 LOG_I2C_DEVICE(this);
57}
59 // Setup read from 0x0 register base
60 const uint8_t reg_base = 0x0;
61 const ErrorCode write_result = this->write(&reg_base, 1);
62 // Just read the entire register map in a bulk read, faster than individually querying register.
63 const ErrorCode read_result = this->read(register_map_, sizeof(register_map_));
64 if (write_result != ErrorCode::ERROR_OK || read_result != ErrorCode::ERROR_OK) {
65 ESP_LOGW(TAG, "MAX9611 Update FAILED!");
66 return;
67 }
68 uint16_t csa_register = ((register_map_[CSA_DATA_BYTE_MSB_ADRR] << 8) | (register_map_[CSA_DATA_BYTE_LSB_ADRR])) >> 4;
69 uint16_t rs_register = ((register_map_[RS_DATA_BYTE_MSB_ADRR] << 8) | (register_map_[RS_DATA_BYTE_LSB_ADRR])) >> 4;
70 uint16_t t_register = ((register_map_[TEMP_DATA_BYTE_MSB_ADRR] << 8) | (register_map_[TEMP_DATA_BYTE_LSB_ADRR])) >> 7;
71 float voltage = rs_register * VOUT_LSB;
72 float shunt_voltage = (csa_register * gain_to_lsb(gain_)) / MICRO_VOLTS_PER_VOLT;
73 float temp = signextend<signed int, 9>(t_register) * TEMP_LSB;
74 float amps = shunt_voltage / current_resistor_;
75 float watts = amps * voltage;
76
77 if (voltage_sensor_ != nullptr) {
79 }
80 if (current_sensor_ != nullptr) {
82 }
83 if (watt_sensor_ != nullptr) {
85 }
86 if (temperature_sensor_ != nullptr) {
88 }
89
90 ESP_LOGD(TAG, "V: %f, A: %f, W: %f, Deg C: %f", voltage, amps, watts, temp);
91}
92} // namespace max9611
93} // namespace esphome
ErrorCode write(const uint8_t *data, size_t len, bool stop=true)
writes an array of bytes to a device using an I2CBus
Definition i2c.h:190
ErrorCode read(uint8_t *data, size_t len)
reads an array of bytes from the device using an I2CBus
Definition i2c.h:164
sensor::Sensor * current_sensor_
Definition max9611.h:53
sensor::Sensor * temperature_sensor_
Definition max9611.h:55
sensor::Sensor * watt_sensor_
Definition max9611.h:54
sensor::Sensor * voltage_sensor_
Definition max9611.h:52
void publish_state(float state)
Publish a new state to the front-end.
Definition sensor.cpp:39
AlsGain501 gain
ErrorCode
Error codes returned by I2CBus and I2CDevice methods.
Definition i2c_bus.h:11
T signextend(const T x)
Definition max9611.cpp:9
float gain_to_lsb(MAX9611Multiplexer gain)
Definition max9611.cpp:16
@ TEMP_DATA_BYTE_LSB_ADRR
Definition max9611.h:32
@ CONTROL_REGISTER_1_ADRR
Definition max9611.h:33
@ RS_DATA_BYTE_MSB_ADRR
Definition max9611.h:25
@ CSA_DATA_BYTE_MSB_ADRR
Definition max9611.h:23
@ RS_DATA_BYTE_LSB_ADRR
Definition max9611.h:26
@ CSA_DATA_BYTE_LSB_ADRR
Definition max9611.h:24
@ TEMP_DATA_BYTE_MSB_ADRR
Definition max9611.h:31
@ MAX9611_MULTIPLEXER_CSA_GAIN4
Definition max9611.h:13
@ MAX9611_MULTIPLEXER_CSA_GAIN1
Definition max9611.h:12
@ MAX9611_MULTIPLEXER_FAST_MODE
Definition max9611.h:19
@ MAX9611_MULTIPLEXER_CSA_GAIN8
Definition max9611.h:14
Providing packet encoding functions for exchanging data with a remote host.
Definition a01nyub.cpp:7
void IRAM_ATTR HOT delay(uint32_t ms)
Definition core.cpp:28
uint16_t x
Definition tt21100.cpp:5