17 static const char *
const TAG =
"ade7880";
22 if (this->irq0_pin_ !=
nullptr) {
23 this->irq0_pin_->setup();
25 this->irq1_pin_->setup();
26 if (this->reset_pin_ !=
nullptr) {
27 this->reset_pin_->setup();
29 this->store_.irq1_pin = this->irq1_pin_->to_isr();
33 if (this->irq1_pin_->digital_read() == 0) {
34 ESP_LOGD(TAG,
"IRQ1 found asserted during setup()");
35 auto status1 = read_u32_register16_(
STATUS1);
38 ESP_LOGD(TAG,
"IRQ1 asserted for !RSTDONE, resetting device");
39 this->reset_device_();
44 ESP_LOGD(TAG,
"Acknowledging RSTDONE");
45 this->write_u32_register16_(
STATUS0, 0xFFFF);
46 this->write_u32_register16_(
STATUS1, 0xFFFF);
52 this->reset_device_();
57 if (!this->store_.reset_done) {
61 ESP_LOGD(TAG,
"Acknowledging RSTDONE");
62 this->write_u32_register16_(
STATUS0, 0xFFFF);
63 this->write_u32_register16_(
STATUS1, 0xFFFF);
65 this->store_.reset_done =
false;
66 this->store_.reset_pending =
false;
71 if (sensor ==
nullptr) {
75 float val = this->read_s24zp_register16_(a_register);
81 if (sensor ==
nullptr) {
85 float val = this->read_s16_register16_(a_register);
91 if (sensor ==
nullptr) {
95 float val = this->read_s32_register16_(a_register);
100 if (this->store_.reset_pending) {
106 if (this->channel_n_ !=
nullptr) {
107 auto *chan = this->channel_n_;
108 this->update_sensor_from_s24zp_register16_(chan->current,
NIRMS, [](
float val) { return val / 100000.0f; });
111 if (this->channel_a_ !=
nullptr) {
112 auto *chan = this->channel_a_;
113 this->update_sensor_from_s24zp_register16_(chan->current,
AIRMS, [](
float val) { return val / 100000.0f; });
114 this->update_sensor_from_s24zp_register16_(chan->voltage,
BVRMS, [](
float val) { return val / 10000.0f; });
115 this->update_sensor_from_s24zp_register16_(chan->active_power,
AWATT, [](
float val) { return val / 100.0f; });
116 this->update_sensor_from_s24zp_register16_(chan->apparent_power,
AVA, [](
float val) { return val / 100.0f; });
117 this->update_sensor_from_s16_register16_(chan->power_factor,
APF,
118 [](
float val) { return std::abs(val / -327.68f); });
119 this->update_sensor_from_s32_register16_(chan->forward_active_energy,
AFWATTHR, [&chan](
float val) {
120 return chan->forward_active_energy_total += val / 14400.0f;
122 this->update_sensor_from_s32_register16_(chan->reverse_active_energy,
AFWATTHR, [&chan](
float val) {
123 return chan->reverse_active_energy_total += val / 14400.0f;
127 if (this->channel_b_ !=
nullptr) {
128 auto *chan = this->channel_b_;
129 this->update_sensor_from_s24zp_register16_(chan->current,
BIRMS, [](
float val) { return val / 100000.0f; });
130 this->update_sensor_from_s24zp_register16_(chan->voltage,
BVRMS, [](
float val) { return val / 10000.0f; });
131 this->update_sensor_from_s24zp_register16_(chan->active_power,
BWATT, [](
float val) { return val / 100.0f; });
132 this->update_sensor_from_s24zp_register16_(chan->apparent_power,
BVA, [](
float val) { return val / 100.0f; });
133 this->update_sensor_from_s16_register16_(chan->power_factor,
BPF,
134 [](
float val) { return std::abs(val / -327.68f); });
135 this->update_sensor_from_s32_register16_(chan->forward_active_energy,
BFWATTHR, [&chan](
float val) {
136 return chan->forward_active_energy_total += val / 14400.0f;
138 this->update_sensor_from_s32_register16_(chan->reverse_active_energy,
BFWATTHR, [&chan](
float val) {
139 return chan->reverse_active_energy_total += val / 14400.0f;
143 if (this->channel_c_ !=
nullptr) {
144 auto *chan = this->channel_c_;
145 this->update_sensor_from_s24zp_register16_(chan->current,
CIRMS, [](
float val) { return val / 100000.0f; });
146 this->update_sensor_from_s24zp_register16_(chan->voltage,
CVRMS, [](
float val) { return val / 10000.0f; });
147 this->update_sensor_from_s24zp_register16_(chan->active_power,
CWATT, [](
float val) { return val / 100.0f; });
148 this->update_sensor_from_s24zp_register16_(chan->apparent_power,
CVA, [](
float val) { return val / 100.0f; });
149 this->update_sensor_from_s16_register16_(chan->power_factor,
CPF,
150 [](
float val) { return std::abs(val / -327.68f); });
151 this->update_sensor_from_s32_register16_(chan->forward_active_energy,
CFWATTHR, [&chan](
float val) {
152 return chan->forward_active_energy_total += val / 14400.0f;
154 this->update_sensor_from_s32_register16_(chan->reverse_active_energy,
CFWATTHR, [&chan](
float val) {
155 return chan->reverse_active_energy_total += val / 14400.0f;
159 ESP_LOGD(TAG,
"update took %u ms",
millis() - start);
163 ESP_LOGCONFIG(TAG,
"ADE7880:");
164 LOG_PIN(
" IRQ0 Pin: ", this->irq0_pin_);
165 LOG_PIN(
" IRQ1 Pin: ", this->irq1_pin_);
166 LOG_PIN(
" RESET Pin: ", this->reset_pin_);
167 ESP_LOGCONFIG(TAG,
" Frequency: %.0f Hz", this->frequency_);
169 if (this->channel_a_ !=
nullptr) {
170 ESP_LOGCONFIG(TAG,
" Phase A:");
171 LOG_SENSOR(
" ",
"Current", this->channel_a_->current);
172 LOG_SENSOR(
" ",
"Voltage", this->channel_a_->voltage);
173 LOG_SENSOR(
" ",
"Active Power", this->channel_a_->active_power);
174 LOG_SENSOR(
" ",
"Apparent Power", this->channel_a_->apparent_power);
175 LOG_SENSOR(
" ",
"Power Factor", this->channel_a_->power_factor);
176 LOG_SENSOR(
" ",
"Forward Active Energy", this->channel_a_->forward_active_energy);
177 LOG_SENSOR(
" ",
"Reverse Active Energy", this->channel_a_->reverse_active_energy);
178 ESP_LOGCONFIG(TAG,
" Calibration:");
179 ESP_LOGCONFIG(TAG,
" Current: %u", this->channel_a_->current_gain_calibration);
180 ESP_LOGCONFIG(TAG,
" Voltage: %d", this->channel_a_->voltage_gain_calibration);
181 ESP_LOGCONFIG(TAG,
" Power: %d", this->channel_a_->power_gain_calibration);
182 ESP_LOGCONFIG(TAG,
" Phase Angle: %u", this->channel_a_->phase_angle_calibration);
185 if (this->channel_b_ !=
nullptr) {
186 ESP_LOGCONFIG(TAG,
" Phase B:");
187 LOG_SENSOR(
" ",
"Current", this->channel_b_->current);
188 LOG_SENSOR(
" ",
"Voltage", this->channel_b_->voltage);
189 LOG_SENSOR(
" ",
"Active Power", this->channel_b_->active_power);
190 LOG_SENSOR(
" ",
"Apparent Power", this->channel_b_->apparent_power);
191 LOG_SENSOR(
" ",
"Power Factor", this->channel_b_->power_factor);
192 LOG_SENSOR(
" ",
"Forward Active Energy", this->channel_b_->forward_active_energy);
193 LOG_SENSOR(
" ",
"Reverse Active Energy", this->channel_b_->reverse_active_energy);
194 ESP_LOGCONFIG(TAG,
" Calibration:");
195 ESP_LOGCONFIG(TAG,
" Current: %u", this->channel_b_->current_gain_calibration);
196 ESP_LOGCONFIG(TAG,
" Voltage: %d", this->channel_b_->voltage_gain_calibration);
197 ESP_LOGCONFIG(TAG,
" Power: %d", this->channel_b_->power_gain_calibration);
198 ESP_LOGCONFIG(TAG,
" Phase Angle: %u", this->channel_b_->phase_angle_calibration);
201 if (this->channel_c_ !=
nullptr) {
202 ESP_LOGCONFIG(TAG,
" Phase C:");
203 LOG_SENSOR(
" ",
"Current", this->channel_c_->current);
204 LOG_SENSOR(
" ",
"Voltage", this->channel_c_->voltage);
205 LOG_SENSOR(
" ",
"Active Power", this->channel_c_->active_power);
206 LOG_SENSOR(
" ",
"Apparent Power", this->channel_c_->apparent_power);
207 LOG_SENSOR(
" ",
"Power Factor", this->channel_c_->power_factor);
208 LOG_SENSOR(
" ",
"Forward Active Energy", this->channel_c_->forward_active_energy);
209 LOG_SENSOR(
" ",
"Reverse Active Energy", this->channel_c_->reverse_active_energy);
210 ESP_LOGCONFIG(TAG,
" Calibration:");
211 ESP_LOGCONFIG(TAG,
" Current: %u", this->channel_c_->current_gain_calibration);
212 ESP_LOGCONFIG(TAG,
" Voltage: %d", this->channel_c_->voltage_gain_calibration);
213 ESP_LOGCONFIG(TAG,
" Power: %d", this->channel_c_->power_gain_calibration);
214 ESP_LOGCONFIG(TAG,
" Phase Angle: %u", this->channel_c_->phase_angle_calibration);
217 if (this->channel_n_ !=
nullptr) {
218 ESP_LOGCONFIG(TAG,
" Neutral:");
219 LOG_SENSOR(
" ",
"Current", this->channel_n_->current);
220 ESP_LOGCONFIG(TAG,
" Calibration:");
221 ESP_LOGCONFIG(TAG,
" Current: %u", this->channel_n_->current_gain_calibration);
224 LOG_I2C_DEVICE(
this);
225 LOG_UPDATE_INTERVAL(
this);
229 if (calibration == 0) {
233 this->write_s10zp_register16_(a_register, calibration);
237 if (calibration == 0) {
241 this->write_s24zpse_register16_(a_register, calibration);
247 this->write_u16_register16_(
GAIN, 0);
249 if (this->frequency_ > 55) {
253 if (this->channel_n_ !=
nullptr) {
254 this->calibrate_s24zpse_reading_(
NIGAIN, this->channel_n_->current_gain_calibration);
257 if (this->channel_a_ !=
nullptr) {
258 this->calibrate_s24zpse_reading_(
AIGAIN, this->channel_a_->current_gain_calibration);
259 this->calibrate_s24zpse_reading_(
AVGAIN, this->channel_a_->voltage_gain_calibration);
260 this->calibrate_s24zpse_reading_(
APGAIN, this->channel_a_->power_gain_calibration);
261 this->calibrate_s10zp_reading_(
APHCAL, this->channel_a_->phase_angle_calibration);
264 if (this->channel_b_ !=
nullptr) {
265 this->calibrate_s24zpse_reading_(
BIGAIN, this->channel_b_->current_gain_calibration);
266 this->calibrate_s24zpse_reading_(
BVGAIN, this->channel_b_->voltage_gain_calibration);
267 this->calibrate_s24zpse_reading_(
BPGAIN, this->channel_b_->power_gain_calibration);
268 this->calibrate_s10zp_reading_(
BPHCAL, this->channel_b_->phase_angle_calibration);
271 if (this->channel_c_ !=
nullptr) {
272 this->calibrate_s24zpse_reading_(
CIGAIN, this->channel_c_->current_gain_calibration);
273 this->calibrate_s24zpse_reading_(
CVGAIN, this->channel_c_->voltage_gain_calibration);
274 this->calibrate_s24zpse_reading_(
CPGAIN, this->channel_c_->power_gain_calibration);
275 this->calibrate_s10zp_reading_(
CPHCAL, this->channel_c_->phase_angle_calibration);
279 this->write_s32_register16_(
VLEVEL, 0);
280 this->write_s32_register16_(
VLEVEL, 0);
281 this->write_s32_register16_(
VLEVEL, 0);
289 if (this->reset_pin_ !=
nullptr) {
290 ESP_LOGD(TAG,
"Reset device using RESET pin");
291 this->reset_pin_->digital_write(
false);
293 this->reset_pin_->digital_write(
true);
295 ESP_LOGD(TAG,
"Reset device using SWRST command");
298 this->store_.reset_pending =
true;
constexpr uint16_t DSPWP_SEL
constexpr uint16_t BVGAIN
constexpr uint16_t CIGAIN
constexpr uint16_t CONFIG2
constexpr uint16_t STATUS0
constexpr uint16_t CONFIG
constexpr uint16_t AVGAIN
constexpr uint16_t CVGAIN
constexpr uint16_t CPHCAL
constexpr uint16_t CONFIG_SWRST
constexpr uint16_t COMPMODE
constexpr uint16_t APGAIN
uint32_t IRAM_ATTR HOT millis()
constexpr uint16_t CFWATTHR
constexpr uint16_t STATUS1
constexpr uint16_t BIGAIN
constexpr uint16_t CPGAIN
static void gpio_intr(ADE7880Store *arg)
constexpr uint16_t BFWATTHR
constexpr uint16_t COMPMODE_DEFAULT
constexpr uint16_t DSPWP_SET
void publish_state(float state)
Publish a new state to the front-end.
void update_sensor_from_s32_register16_(sensor::Sensor *sensor, uint16_t a_register, F &&f)
constexpr uint8_t CONFIG2_I2C_LOCK
constexpr uint16_t RUN_ENABLE
void update_sensor_from_s16_register16_(sensor::Sensor *sensor, uint16_t a_register, F &&f)
constexpr uint8_t DSPWP_SET_RO
constexpr uint8_t DSPWP_SEL_SET
void update_sensor_from_s24zp_register16_(sensor::Sensor *sensor, uint16_t a_register, F &&f)
constexpr uint16_t BPHCAL
constexpr uint16_t NIGAIN
constexpr uint16_t AIGAIN
constexpr uint16_t COMPMODE_SELFREQ
constexpr uint32_t STATUS1_RSTDONE
void dump_config() override
void calibrate_s10zp_reading_(uint16_t a_register, int16_t calibration)
constexpr uint16_t APHCAL
constexpr uint16_t VLEVEL
This is a workaround until we can figure out a way to get the tflite-micro idf component code availab...
void calibrate_s24zpse_reading_(uint16_t a_register, int32_t calibration)
Base-class for all sensors.
constexpr uint16_t AFWATTHR
constexpr uint16_t BPGAIN
void IRAM_ATTR HOT delay(uint32_t ms)