From 33ce9096d78345b9a35ff75ed27bbb9c91848d16 Mon Sep 17 00:00:00 2001 From: lovyan03 <42724151+lovyan03@users.noreply.github.com> Date: Tue, 5 Nov 2024 12:42:58 +0900 Subject: [PATCH] tweak for ESP-IDF v5 --- src/lgfx/v1/gitTagVersion.h | 2 +- src/lgfx/v1/panel/Panel_M5HDMI.cpp | 96 +++++++++++++++++++++++-- src/lgfx/v1/panel/Panel_M5HDMI.hpp | 5 +- src/lgfx/v1/platforms/esp32/Bus_SPI.cpp | 8 +-- src/lgfx/v1/platforms/esp32/common.cpp | 81 +++++++++++++++------ src/lgfx/v1/platforms/esp32/common.hpp | 24 +++++-- 6 files changed, 174 insertions(+), 42 deletions(-) diff --git a/src/lgfx/v1/gitTagVersion.h b/src/lgfx/v1/gitTagVersion.h index 1bfee162..277f024d 100644 --- a/src/lgfx/v1/gitTagVersion.h +++ b/src/lgfx/v1/gitTagVersion.h @@ -1,4 +1,4 @@ #define LGFX_VERSION_MAJOR 1 #define LGFX_VERSION_MINOR 1 -#define LGFX_VERSION_PATCH 16 +#define LGFX_VERSION_PATCH 17 #define LOVYANGFX_VERSION F( LGFX_VERSION_MAJOR "." LGFX_VERSION_MINOR "." LGFX_VERSION_PATCH ) diff --git a/src/lgfx/v1/panel/Panel_M5HDMI.cpp b/src/lgfx/v1/panel/Panel_M5HDMI.cpp index 07785d90..906413a7 100644 --- a/src/lgfx/v1/panel/Panel_M5HDMI.cpp +++ b/src/lgfx/v1/panel/Panel_M5HDMI.cpp @@ -347,10 +347,67 @@ namespace lgfx return true; } + void Panel_M5HDMI::HDMI_Trans::_i2c_backup(void) + { + int i2c_port = HDMI_Trans_config.i2c_port; + auto sda = lgfx::i2c::getPinSDA(i2c_port); + int prev_sda = -1; + if (sda.has_value()) + { + prev_sda = sda.value(); + } + _pin_backup[0].setPin(prev_sda); + _pin_backup[0].backup(); + + auto scl = lgfx::i2c::getPinSCL(i2c_port); + int prev_scl = -1; + if (scl.has_value()) + { + prev_scl = scl.value(); + } + _pin_backup[1].setPin(prev_scl); + _pin_backup[1].backup(); + + int new_sda = _pin_backup[2].getPin(); + int new_scl = _pin_backup[3].getPin(); + if (new_sda >= 0 && new_scl >= 0) + { + if (prev_sda != new_sda || prev_scl != new_scl) + { + // lgfx::i2c::setPins(i2c_port, new_sda, new_scl); + lgfx::i2c::init(i2c_port, new_sda, new_scl); + const uint8_t gpio_command[] = { + lgfx::gpio::command_mode_output, (uint8_t)new_scl, + lgfx::gpio::command_write_low , (uint8_t)new_scl, + lgfx::gpio::command_mode_output, (uint8_t)new_sda, + lgfx::gpio::command_write_low , (uint8_t)new_sda, + lgfx::gpio::command_write_high , (uint8_t)new_scl, + lgfx::gpio::command_write_high , (uint8_t)new_sda, + lgfx::gpio::command_write_low , (uint8_t)new_scl, + lgfx::gpio::command_write_low , (uint8_t)new_sda, + lgfx::gpio::command_write_high , (uint8_t)new_scl, + lgfx::gpio::command_write_high , (uint8_t)new_sda, + lgfx::gpio::command_end + }; + lgfx::gpio::command(gpio_command); + _pin_backup[2].restore(); + _pin_backup[3].restore(); + } + } + } + + void Panel_M5HDMI::HDMI_Trans::_i2c_restore(void) + { + lgfx::i2c::init(HDMI_Trans_config.i2c_port, _pin_backup[0].getPin(), _pin_backup[1].getPin()); + _pin_backup[0].restore(); + _pin_backup[1].restore(); + } + Panel_M5HDMI::HDMI_Trans::ChipID Panel_M5HDMI::HDMI_Trans::readChipID(void) { ChipID chip_id = { 0,0,0 }; + _i2c_backup(); if (this->writeRegister(0xff, 0x80) && this->writeRegister(0xee, 0x01)) { @@ -358,18 +415,39 @@ namespace lgfx chip_id.id[1] = this->readRegister(0x01); chip_id.id[2] = this->readRegister(0x02); } + _i2c_restore(); + return chip_id; } void Panel_M5HDMI::HDMI_Trans::reset(void) { + _i2c_backup(); static constexpr const uint8_t data[] = { 0xff, 0x81, 0x30, 0x00, 0x02, 0x66, 0x0a, 0x06, 0x15, 0x06, 0x4e, 0xa8, 0xff, 0x80, 0xee, 0x01, 0x11, 0x00, 0x13, 0xf1, 0x13, 0xf9, 0x0a, 0x80, 0xff, 0x82, 0x1b, 0x77, 0x1c, 0xec, 0x45, 0x00, 0x4f, 0x40, 0x50, 0x00, 0x47, 0x07 }; this->writeRegisterSet(data, sizeof(data)); + _i2c_restore(); + } + + Panel_M5HDMI::HDMI_Trans::HDMI_Trans(const lgfx::Bus_I2C::config_t& i2c_config) + { + HDMI_Trans_config.i2c_port = i2c_config.i2c_port; + // _pin_backup[2].setPin(GPIO_NUM_NC); + // _pin_backup[3].setPin(GPIO_NUM_NC); + _i2c_backup(); + HDMI_Trans_config = i2c_config; + lgfx::i2c::release(HDMI_Trans_config.i2c_port); + lgfx::i2c::init(HDMI_Trans_config.i2c_port, HDMI_Trans_config.pin_sda, HDMI_Trans_config.pin_scl); + _pin_backup[2].setPin(HDMI_Trans_config.pin_sda); + _pin_backup[3].setPin(HDMI_Trans_config.pin_scl); + _pin_backup[2].backup(); + _pin_backup[3].backup(); + _i2c_restore(); } bool Panel_M5HDMI::HDMI_Trans::init(void) { auto id = this->readChipID(); + _i2c_backup(); { // 96kHz audio setting. // static constexpr const uint8_t data_1[] = { 0xff, 0x82, 0xD6, 0x8E, 0xD7, 0x04, 0xff, 0x84, 0x06, 0x08, 0x07, 0x10, 0x09, 0x00, 0x0F, 0xAB, 0x34, 0xD5, 0x35, 0x00, 0x36, 0x30, 0x37, 0x00, 0x3C, 0x21, @@ -393,6 +471,7 @@ namespace lgfx this->writeRegisterSet(data_u3, sizeof(data_u3)); } + bool result = false; for (int i = 0; i < 8; ++i) { static constexpr const uint8_t data_pll[] = { 0xff, 0x80, 0x16, 0xf1, 0x18, 0xdc, 0x18, 0xfc, 0x16, 0xf3, 0x16, 0xe3, 0x16, 0xf3, 0xff, 0x82 }; @@ -404,15 +483,21 @@ namespace lgfx { static constexpr const uint8_t data[] = { 0xb9, 0x00, 0xff, 0x84, 0x43, 0x31, 0x44, 0x10, 0x45, 0x2a, 0x47, 0x04, 0x10, 0x2c, 0x12, 0x64, 0x3d, 0x0a, 0xff, 0x80, 0x11, 0x00, 0x13, 0xf1, 0x13, 0xf9, 0xff, 0x81, 0x31, 0x44, 0x32, 0x4a, 0x33, 0x0b, 0x34, 0x00, 0x35, 0x00, 0x36, 0x00, 0x37, 0x44, 0x3f, 0x0f, 0x40, 0xa0, 0x41, 0xa0, 0x42, 0xa0, 0x43, 0xa0, 0x44, 0xa0, 0x30, 0xea }; this->writeRegisterSet(data, sizeof(data)); - return true; + result = true; + break; } } - ESP_LOGE(TAG, "failed to initialize the HDMI transmitter."); - return false; + _i2c_restore(); + if (!result) { + ESP_LOGE(TAG, "failed to initialize the HDMI transmitter."); + return false; + } + return true; } size_t Panel_M5HDMI::HDMI_Trans::readEDID(uint8_t* EDID, size_t len) { + _i2c_backup(); static constexpr const uint8_t data[] = { 0xff, 0x85 ,0x03, 0xc9 ,0x04, 0xA0 ,0x06, 0x20 ,0x14, 0x7f }; this->writeRegisterSet(data, sizeof(data)); @@ -440,6 +525,7 @@ namespace lgfx } static constexpr const uint8_t data3[] = { 0x03, 0xc2 ,0x07, 0x1f }; this->writeRegisterSet(data3, sizeof(data3)); + _i2c_restore(); return result; } @@ -467,10 +553,8 @@ namespace lgfx { ESP_LOGI(TAG, "i2c port:%d sda:%d scl:%d", _HDMI_Trans_config.i2c_port, _HDMI_Trans_config.pin_sda, _HDMI_Trans_config.pin_scl); - lgfx::i2c::init(_HDMI_Trans_config.i2c_port, _HDMI_Trans_config.pin_sda, _HDMI_Trans_config.pin_scl); - HDMI_Trans driver(_HDMI_Trans_config); - + auto result = driver.readChipID(); ESP_LOGI(TAG, "Chip ID: %02x %02x %02x", result.id[0], result.id[1], result.id[2]); if (result.id[0] == result.id[1] && result.id[0] == result.id[2]) diff --git a/src/lgfx/v1/panel/Panel_M5HDMI.hpp b/src/lgfx/v1/panel/Panel_M5HDMI.hpp index cc5f274d..6b3f9fd1 100644 --- a/src/lgfx/v1/panel/Panel_M5HDMI.hpp +++ b/src/lgfx/v1/panel/Panel_M5HDMI.hpp @@ -214,6 +214,9 @@ namespace lgfx typedef lgfx::Bus_I2C::config_t config_t; private: config_t HDMI_Trans_config; + gpio::pin_backup_t _pin_backup[4]; + void _i2c_backup(void); + void _i2c_restore(void); uint8_t readRegister(uint8_t register_address); uint16_t readRegister16(uint8_t register_address); @@ -227,7 +230,7 @@ namespace lgfx uint8_t id[3]; }; - HDMI_Trans(const lgfx::Bus_I2C::config_t& i2c_config) : HDMI_Trans_config(i2c_config) {} + HDMI_Trans(const lgfx::Bus_I2C::config_t& i2c_config); HDMI_Trans(const HDMI_Trans&) = delete; HDMI_Trans(HDMI_Trans&&) = delete; ChipID readChipID(void); diff --git a/src/lgfx/v1/platforms/esp32/Bus_SPI.cpp b/src/lgfx/v1/platforms/esp32/Bus_SPI.cpp index 15c5070b..5ee139e2 100644 --- a/src/lgfx/v1/platforms/esp32/Bus_SPI.cpp +++ b/src/lgfx/v1/platforms/esp32/Bus_SPI.cpp @@ -20,12 +20,7 @@ Original Source: #include "Bus_SPI.hpp" -/// ESP32-S3をターゲットにした際にREG_SPI_BASEが定義されていなかったので応急処置 ; -#if defined ( CONFIG_IDF_TARGET_ESP32S3 ) - #if !defined( REG_SPI_BASE ) - #define REG_SPI_BASE(i) (DR_REG_SPI1_BASE + (((i)>1) ? (((i)* 0x1000) + 0x20000) : (((~(i)) & 1)* 0x1000 ))) - #endif -#elif defined ( CONFIG_IDF_TARGET_ESP32 ) || !defined ( CONFIG_IDF_TARGET ) +#if defined ( CONFIG_IDF_TARGET_ESP32 ) || !defined ( CONFIG_IDF_TARGET ) #define LGFX_SPIDMA_WORKAROUND #endif @@ -613,6 +608,7 @@ namespace lgfx goto label_start; do { + vTaskDelay(1 / portTICK_PERIOD_MS); while (*cmd & SPI_USR) {} label_start: exec_spi(); diff --git a/src/lgfx/v1/platforms/esp32/common.cpp b/src/lgfx/v1/platforms/esp32/common.cpp index b6511a07..fb472a62 100644 --- a/src/lgfx/v1/platforms/esp32/common.cpp +++ b/src/lgfx/v1/platforms/esp32/common.cpp @@ -348,10 +348,17 @@ namespace lgfx _gpio_pin_reg = *reinterpret_cast(GPIO_PIN0_REG + (pin_num * 4)); _gpio_func_out_reg = *reinterpret_cast(GPIO_FUNC0_OUT_SEL_CFG_REG + (pin_num * 4)); #if defined ( GPIO_ENABLE1_REG ) - _gpio_enable = *reinterpret_cast(((_pin_num & 32) ? GPIO_ENABLE1_REG : GPIO_ENABLE_REG)) & (1 << (_pin_num & 31)); + _gpio_enable = *reinterpret_cast(((pin_num & 32) ? GPIO_ENABLE1_REG : GPIO_ENABLE_REG)) & (1 << (pin_num & 31)); #else - _gpio_enable = *reinterpret_cast(GPIO_ENABLE_REG) & (1 << (_pin_num & 31)); -#endif + _gpio_enable = *reinterpret_cast(GPIO_ENABLE_REG) & (1 << (pin_num & 31)); +#endif + _in_func_num = -1; + size_t func_num = GPIO.func_out_sel_cfg[pin_num].func_sel; + if (func_num < 256 && pin_num == GPIO.func_in_sel_cfg[func_num].func_sel) { + _gpio_func_in_reg = GPIO.func_in_sel_cfg[func_num].val; + _in_func_num = func_num; +// ESP_LOGD("DEBUG","backup pin:%d : func_num:%d", pin_num, _in_func_num); + } } } @@ -360,22 +367,28 @@ namespace lgfx auto pin_num = (size_t)_pin_num; if (pin_num < GPIO_NUM_MAX) { - // ESP_LOGD("DEBUG","restore pin:%d ", _pin_num); - // ESP_LOGD("DEBUG","restore IO_MUX_GPIO0_REG :%08x -> %08x ", *reinterpret_cast(GPIO_PIN_MUX_REG[_pin_num] ), _io_mux_gpio_reg ); - // ESP_LOGD("DEBUG","restore GPIO_PIN0_REG :%08x -> %08x ", *reinterpret_cast(GPIO_PIN0_REG + (_pin_num * 4)), _gpio_pin_reg ); - // ESP_LOGD("DEBUG","restore GPIO_FUNC0_OUT_SEL_CFG_REG:%08x -> %08x ", *reinterpret_cast(GPIO_FUNC0_OUT_SEL_CFG_REG + (_pin_num * 4)), _gpio_func_out_reg ); + if ((uint16_t)_in_func_num < 256) { + GPIO.func_in_sel_cfg[_in_func_num].val = _gpio_func_in_reg; + // ESP_LOGD("DEBUG","pin:%d in_func_num:%d", (int)pin_num, (int)_in_func_num); + } + + // ESP_LOGD("DEBUG","restore pin:%d ", pin_num); + // ESP_LOGD("DEBUG","restore IO_MUX_GPIO0_REG :%08x -> %08x ", *reinterpret_cast(GPIO_PIN_MUX_REG[pin_num] ), _io_mux_gpio_reg ); + // ESP_LOGD("DEBUG","restore GPIO_PIN0_REG :%08x -> %08x ", *reinterpret_cast(GPIO_PIN0_REG + (pin_num * 4)), _gpio_pin_reg ); + // ESP_LOGD("DEBUG","restore GPIO_FUNC0_OUT_SEL_CFG_REG:%08x -> %08x ", *reinterpret_cast(GPIO_FUNC0_OUT_SEL_CFG_REG + (pin_num * 4)), _gpio_func_out_reg ); *reinterpret_cast(GPIO_PIN_MUX_REG[_pin_num]) = _io_mux_gpio_reg; - *reinterpret_cast(GPIO_PIN0_REG + (_pin_num * 4)) = _gpio_pin_reg; - *reinterpret_cast(GPIO_FUNC0_OUT_SEL_CFG_REG + (_pin_num * 4)) = _gpio_func_out_reg; + *reinterpret_cast(GPIO_PIN0_REG + (pin_num * 4)) = _gpio_pin_reg; + *reinterpret_cast(GPIO_FUNC0_OUT_SEL_CFG_REG + (pin_num * 4)) = _gpio_func_out_reg; + #if defined ( GPIO_ENABLE1_REG ) - auto gpio_enable_reg = reinterpret_cast(((_pin_num & 32) ? GPIO_ENABLE1_REG : GPIO_ENABLE_REG)); + auto gpio_enable_reg = reinterpret_cast(((pin_num & 32) ? GPIO_ENABLE1_REG : GPIO_ENABLE_REG)); #else auto gpio_enable_reg = reinterpret_cast(GPIO_ENABLE_REG); #endif - uint32_t pin_mask = 1 << (_pin_num & 31); + uint32_t pin_mask = 1 << (pin_num & 31); uint32_t val = *gpio_enable_reg; - // ESP_LOGD("DEBUG","restore GPIO_ENABLE_REG:%08x", *gpio_enable_reg); + // ESP_LOGD("DEBUG","restore GPIO_ENABLE_REG:%08x", (int)*gpio_enable_reg); if (_gpio_enable) { val |= pin_mask; @@ -385,7 +398,6 @@ namespace lgfx val &= ~pin_mask; } *gpio_enable_reg = val; - // ESP_LOGD("DEBUG","restore GPIO_ENABLE_REG:%08x", *gpio_enable_reg); } } @@ -480,7 +492,12 @@ namespace lgfx } if (_spi_handle[spi_host] == nullptr) { - _spi_handle[spi_host] = spiStartBus(spi_port, SPI_CLK_EQU_SYSCLK, 0, 0); + auto spi_num = spi_port; +#if defined ( CONFIG_IDF_TARGET_ESP32S3 ) + spi_num = HSPI; + if (spi_host == SPI2_HOST) { spi_num = FSPI; } +#endif + _spi_handle[spi_host] = spiStartBus(spi_num, SPI_CLK_EQU_SYSCLK, 0, 0); } #endif @@ -671,17 +688,10 @@ namespace lgfx #define I2C_ACK_ERR_INT_RAW_M I2C_NACK_INT_RAW_M #endif -#if __has_include() - static periph_module_t getPeriphModule(int num) - { - return i2c_periph_signal[num].module; - } -#else static periph_module_t getPeriphModule(int num) { return num == 0 ? PERIPH_I2C0_MODULE : PERIPH_I2C1_MODULE; } -#endif static i2c_dev_t* getDev(int num) { @@ -808,7 +818,13 @@ namespace lgfx #endif #endif #endif + +#if SOC_I2C_NUM == 1 || defined CONFIG_IDF_TARGET_ESP32C6 + auto twowire = &Wire; +#else auto twowire = ((dev == &I2C0) ? &Wire : &Wire1); +#endif + #if defined ( USE_TWOWIRE_SETPINS ) twowire->setPins(sda, scl); #else @@ -1014,7 +1030,11 @@ namespace lgfx #if ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 0, 0) #if defined ARDUINO_ESP32_GIT_VER #if ARDUINO_ESP32_GIT_VER != 0x44c11981 + #if SOC_I2C_NUM == 1 || defined CONFIG_IDF_TARGET_ESP32C6 + auto twowire = &Wire; + #else auto twowire = ((i2c_port == 1) ? &Wire1 : &Wire); + #endif twowire->end(); #endif #endif @@ -1063,13 +1083,28 @@ namespace lgfx #endif #endif #if defined ( USE_TWOWIRE_SETPINS ) + +#if SOC_I2C_NUM == 1 || defined CONFIG_IDF_TARGET_ESP32C6 + auto twowire = &Wire; +#else auto twowire = ((i2c_port == 1) ? &Wire1 : &Wire); +#endif twowire->setPins(pin_sda, pin_scl); #endif #endif return {}; } + cpp::result getPinSDA(int i2c_port) + { + return i2c_context[i2c_port].pin_sda; + } + + cpp::result getPinSCL(int i2c_port) + { + return i2c_context[i2c_port].pin_scl; + } + cpp::result init(int i2c_port) { if ((i2c_port >= I2C_NUM_MAX) @@ -1085,7 +1120,11 @@ namespace lgfx } #if defined ( ARDUINO ) && __has_include () +#if SOC_I2C_NUM == 1 || defined CONFIG_IDF_TARGET_ESP32C6 + auto twowire = &Wire; +#else auto twowire = ((i2c_port == 1) ? &Wire1 : &Wire); +#endif #if defined ( USE_TWOWIRE_SETPINS ) twowire->begin(); #else diff --git a/src/lgfx/v1/platforms/esp32/common.hpp b/src/lgfx/v1/platforms/esp32/common.hpp index 33ccc432..53305cb1 100644 --- a/src/lgfx/v1/platforms/esp32/common.hpp +++ b/src/lgfx/v1/platforms/esp32/common.hpp @@ -34,12 +34,15 @@ Original Source: #include #include -#if !defined ( REG_SPI_BASE ) - /// ESP32-S3をターゲットにした際にREG_SPI_BASEが定義されていなかったので応急処置 5.3まで; - #if defined ( CONFIG_IDF_TARGET_ESP32S3 ) - #define REG_SPI_BASE(i) (DR_REG_SPI1_BASE + (((i)>1) ? (((i)* 0x1000) + 0x20000) : (((~(i)) & 1)* 0x1000 ))) - #else - //#define REG_SPI_BASE(i) (DR_REG_SPI0_BASE - (i) * 0x1000) + +#if defined ( CONFIG_IDF_TARGET_ESP32S3 ) + /// ESP32-S3をターゲットにした際にREG_SPI_BASEの定義がおかしいため自前で設定 + #if defined( REG_SPI_BASE ) + #undef REG_SPI_BASE + #endif + #define REG_SPI_BASE(i) (DR_REG_SPI1_BASE + (((i)>1) ? (((i)* 0x1000) + 0x20000) : (((~(i)) & 1)* 0x1000 ))) +#else + #if !defined ( REG_SPI_BASE ) #define REG_SPI_BASE(i) (DR_REG_SPI2_BASE) #endif #endif @@ -226,6 +229,9 @@ namespace lgfx { public: pin_backup_t(int pin_num); + pin_backup_t(void) : pin_backup_t( GPIO_NUM_NC ) {}; + void setPin(int pin_num) { _pin_num = pin_num; } + int getPin(void) const { return _pin_num; } void backup(void); void restore(void); @@ -233,7 +239,9 @@ namespace lgfx uint32_t _io_mux_gpio_reg; uint32_t _gpio_pin_reg; uint32_t _gpio_func_out_reg; - gpio_num_t _pin_num; + uint32_t _gpio_func_in_reg; + int16_t _in_func_num = -1;; + int8_t _pin_num = GPIO_NUM_NC; bool _gpio_enable; }; @@ -267,6 +275,8 @@ namespace lgfx { cpp::result setPins(int i2c_port, int pin_sda, int pin_scl); cpp::result init(int i2c_port); + cpp::result getPinSDA(int i2c_port); + cpp::result getPinSCL(int i2c_port); } //----------------------------------------------------------------------------