Add PZEM004T/PZEMAC/PZEMDC Support (#587)

* Add PZEM004T Support

* Don't flush as much

* Update pzem004t.cpp

* Add generalized modbus

* Add PZEMAC

* Add PZEMDC

* Fix file modes

* Lint

* Fix

* Fix

* Add check_uart_settings
This commit is contained in:
Otto Winter
2019-10-20 19:24:20 +02:00
parent 644aec791e
commit d2c7afeef0
26 changed files with 738 additions and 7 deletions
+33 -6
View File
@@ -25,7 +25,10 @@ void UARTComponent::setup() {
}
int8_t tx = this->tx_pin_.has_value() ? *this->tx_pin_ : -1;
int8_t rx = this->rx_pin_.has_value() ? *this->rx_pin_ : -1;
this->hw_serial_->begin(this->baud_rate_, SERIAL_8N1, rx, tx);
uint32_t config = SERIAL_8N1;
if (this->stop_bits_ == 2)
config = SERIAL_8N2;
this->hw_serial_->begin(this->baud_rate_, config, rx, tx);
}
void UARTComponent::dump_config() {
@@ -37,6 +40,7 @@ void UARTComponent::dump_config() {
ESP_LOGCONFIG(TAG, " RX Pin: GPIO%d", *this->rx_pin_);
}
ESP_LOGCONFIG(TAG, " Baud Rate: %u baud", this->baud_rate_);
ESP_LOGCONFIG(TAG, " Stop bits: %u", this->stop_bits_);
}
void UARTComponent::write_byte(uint8_t data) {
@@ -102,21 +106,27 @@ void UARTComponent::setup() {
// Use Arduino HardwareSerial UARTs if all used pins match the ones
// preconfigured by the platform. For example if RX disabled but TX pin
// is 1 we still want to use Serial.
uint32_t mode = UART_NB_BIT_8 | UART_PARITY_NONE;
if (this->stop_bits_ == 1)
mode |= UART_NB_STOP_BIT_1;
else
mode |= UART_NB_STOP_BIT_2;
SerialConfig config = static_cast<SerialConfig>(mode);
if (this->tx_pin_.value_or(1) == 1 && this->rx_pin_.value_or(3) == 3) {
this->hw_serial_ = &Serial;
this->hw_serial_->begin(this->baud_rate_);
this->hw_serial_->begin(this->baud_rate_, config);
} else if (this->tx_pin_.value_or(15) == 15 && this->rx_pin_.value_or(13) == 13) {
this->hw_serial_ = &Serial;
this->hw_serial_->begin(this->baud_rate_);
this->hw_serial_->begin(this->baud_rate_, config);
this->hw_serial_->swap();
} else if (this->tx_pin_.value_or(2) == 2 && this->rx_pin_.value_or(8) == 8) {
this->hw_serial_ = &Serial1;
this->hw_serial_->begin(this->baud_rate_);
this->hw_serial_->begin(this->baud_rate_, config);
} else {
this->sw_serial_ = new ESP8266SoftwareSerial();
int8_t tx = this->tx_pin_.has_value() ? *this->tx_pin_ : -1;
int8_t rx = this->rx_pin_.has_value() ? *this->rx_pin_ : -1;
this->sw_serial_->setup(tx, rx, this->baud_rate_);
this->sw_serial_->setup(tx, rx, this->baud_rate_, this->stop_bits_);
}
}
@@ -129,6 +139,7 @@ void UARTComponent::dump_config() {
ESP_LOGCONFIG(TAG, " RX Pin: GPIO%d", *this->rx_pin_);
}
ESP_LOGCONFIG(TAG, " Baud Rate: %u baud", this->baud_rate_);
ESP_LOGCONFIG(TAG, " Stop bits: %u", this->stop_bits_);
if (this->hw_serial_ != nullptr) {
ESP_LOGCONFIG(TAG, " Using hardware serial interface.");
} else {
@@ -231,7 +242,7 @@ void UARTComponent::flush() {
}
}
void ESP8266SoftwareSerial::setup(int8_t tx_pin, int8_t rx_pin, uint32_t baud_rate) {
void ESP8266SoftwareSerial::setup(int8_t tx_pin, int8_t rx_pin, uint32_t baud_rate, uint8_t stop_bits) {
this->bit_time_ = F_CPU / baud_rate;
if (tx_pin != -1) {
auto pin = GPIOPin(tx_pin, OUTPUT);
@@ -246,6 +257,7 @@ void ESP8266SoftwareSerial::setup(int8_t tx_pin, int8_t rx_pin, uint32_t baud_ra
this->rx_buffer_ = new uint8_t[this->rx_buffer_size_];
pin.attach_interrupt(ESP8266SoftwareSerial::gpio_intr, this, FALLING);
}
this->stop_bits_ = stop_bits;
}
void ICACHE_RAM_ATTR ESP8266SoftwareSerial::gpio_intr(ESP8266SoftwareSerial *arg) {
uint32_t wait = arg->bit_time_ + arg->bit_time_ / 3 - 500;
@@ -262,6 +274,8 @@ void ICACHE_RAM_ATTR ESP8266SoftwareSerial::gpio_intr(ESP8266SoftwareSerial *arg
rec |= arg->read_bit_(&wait, start) << 7;
// Stop bit
arg->wait_(&wait, start);
if (arg->stop_bits_ == 2)
arg->wait_(&wait, start);
arg->rx_buffer_[arg->rx_in_pos_] = rec;
arg->rx_in_pos_ = (arg->rx_in_pos_ + 1) % arg->rx_buffer_size_;
@@ -289,6 +303,8 @@ void ICACHE_RAM_ATTR HOT ESP8266SoftwareSerial::write_byte(uint8_t data) {
this->write_bit_(data & (1 << 7), &wait, start);
// Stop bit
this->write_bit_(true, &wait, start);
if (this->stop_bits_ == 2)
this->wait_(&wait, start);
enable_interrupts();
}
void ICACHE_RAM_ATTR ESP8266SoftwareSerial::wait_(uint32_t *wait, const uint32_t &start) {
@@ -344,5 +360,16 @@ int UARTComponent::peek() {
return data;
}
void UARTDevice::check_uart_settings(uint32_t baud_rate, uint8_t stop_bits) {
if (this->parent_->baud_rate_ != baud_rate) {
ESP_LOGE(TAG, " Invalid baud_rate: Integration requested baud_rate %u but you have %u!", baud_rate,
this->parent_->baud_rate_);
}
if (this->parent_->stop_bits_ != stop_bits) {
ESP_LOGE(TAG, " Invalid stop bits: Integration requested stop_bits %u but you have %u!", stop_bits,
this->parent_->stop_bits_);
}
}
} // namespace uart
} // namespace esphome