From 2c65b21355f697c6ad83842d37002b295e57007a Mon Sep 17 00:00:00 2001 From: rotorman Date: Sat, 10 Jul 2021 10:19:09 +0200 Subject: [PATCH 1/4] Based on PR #408 ff34616 that according to @rcvideoreviews on Discord works. Added: * @olliw42 PR #415 STOP condition fix. * @raphaelcoeffic EXTI_Trigger_Rising * fixed some uint8_t bool confusions * added volatile to touchEventOccured that is set from ISR and accessed from main code * changed to upload GT911 config also if config version is the same --- radio/src/targets/horus/hal.h | 2 +- radio/src/targets/horus/tp_gt911.cpp | 39 ++++++++++++++++++---------- radio/src/targets/horus/tp_gt911.h | 2 +- 3 files changed, 27 insertions(+), 16 deletions(-) diff --git a/radio/src/targets/horus/hal.h b/radio/src/targets/horus/hal.h index 8d7be0da5..cc12222fa 100644 --- a/radio/src/targets/horus/hal.h +++ b/radio/src/targets/horus/hal.h @@ -728,7 +728,7 @@ #define I2C_SCL_GPIO_PinSource GPIO_PinSource8 #define I2C_SDA_GPIO_PinSource GPIO_PinSource9 #endif -#define I2C_SPEED 400000 +#define I2C_SPEED 100000 // Haptic #define HAPTIC_PWM diff --git a/radio/src/targets/horus/tp_gt911.cpp b/radio/src/targets/horus/tp_gt911.cpp index 12a8d8a7a..6b9823dd9 100644 --- a/radio/src/targets/horus/tp_gt911.cpp +++ b/radio/src/targets/horus/tp_gt911.cpp @@ -230,9 +230,9 @@ const uint8_t TOUCH_GT911_Cfg[] = 0x5A, // 0x8053 Screen touch level 0x3C, // 0x8054 Screen touch leave 0x03, // 0x8055 Low power control - 0x05, // 0x8056 Refresh rate - 0x00, // 0x8057 X threshold - 0x00, // 0x8058 Y threshold + 0x0F, // 0x8056 Refresh rate + 0x0A, // 0x8057 X threshold + 0x0A, // 0x8058 Y threshold 0x00, // 0x8059 Reserved 0x00, // 0x805A Reserved 0x11, // 0x805B Space (top, bottom) @@ -403,8 +403,8 @@ const uint8_t TOUCH_GT911_Cfg[] = #endif -uint8_t touchGT911Flag = 0; -uint8_t touchEventOccured = 0; +bool touchGT911Flag = false; +volatile bool touchEventOccured = false; struct TouchData touchData; static void TOUCH_AF_ExtiStop(void) @@ -415,7 +415,7 @@ static void TOUCH_AF_ExtiStop(void) EXTI_StructInit(&EXTI_InitStructure); EXTI_InitStructure.EXTI_Line = TOUCH_INT_EXTI_LINE1; EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; - EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising_Falling; + EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising; EXTI_InitStructure.EXTI_LineCmd = DISABLE; EXTI_Init(&EXTI_InitStructure); @@ -436,7 +436,7 @@ static void TOUCH_AF_ExtiConfig(void) EXTI_StructInit(&EXTI_InitStructure); EXTI_InitStructure.EXTI_Line = TOUCH_INT_EXTI_LINE1; EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; - EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising_Falling; + EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising; EXTI_InitStructure.EXTI_LineCmd = ENABLE; EXTI_Init(&EXTI_InitStructure); @@ -581,6 +581,11 @@ bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return false; + // see GP911 data sheet, chapter 6.1.c, page 12, diagram for reading data + I2C_GenerateSTOP(I2C, ENABLE); + if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) + return false; + I2C_GenerateSTART(I2C, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return false; @@ -607,7 +612,7 @@ bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) return true; } -uint8_t I2C_GT911_SendConfig(uint8_t mode) +void I2C_GT911_SendConfig(uint8_t mode) { uint8_t buf[2]; uint8_t i = 0; @@ -619,12 +624,12 @@ uint8_t I2C_GT911_SendConfig(uint8_t mode) buf[0] = (~buf[0]) + 1; I2C_GT911_WriteRegister(GT_CFGS_REG, (uint8_t *) TOUCH_GT911_Cfg, sizeof(TOUCH_GT911_Cfg));// I2C_GT911_WriteRegister(GT_CHECK_REG, buf, 2);//write checksum - return 0; } void touchPanelDeInit(void) { TOUCH_AF_ExtiStop(); + touchGT911Flag = false; } bool touchPanelInit(void) @@ -666,7 +671,7 @@ bool touchPanelInit(void) I2C_GT911_ReadRegister(GT_CFGS_REG, tmp, 1); TRACE("Chip config Ver:%x\r\n", tmp[0]); - if (tmp[0] < GT911_CFG_NUMER) //Config ver + if (tmp[0] <= GT911_CFG_NUMER) //Config ver { TRACE("Sending new config %d", GT911_CFG_NUMER); I2C_GT911_SendConfig(1); @@ -713,12 +718,15 @@ void touchPanelRead() if (!touchEventOccured) return; - touchEventOccured = 0; + touchEventOccured = false; uint32_t startReadStatus = RTOS_GET_MS(); do { if (!I2C_GT911_ReadRegister(GT911_READ_XY_REG, &state, 1)) { - TRACE("GT911 I2C read error"); + ledRed(); + TRACE("GT911 I2C read XY error"); + touchPanelDeInit(); + touchPanelInit(); return; } @@ -736,7 +744,10 @@ void touchPanelRead() if (pointsCount > 0 && pointsCount <= GT911_MAX_TP) { if (!I2C_GT911_ReadRegister(GT911_READ_XY_REG + 1, touchData.data, pointsCount * sizeof(TouchPoint))) { - TRACE("GT911 I2C read error"); + ledRed(); + TRACE("GT911 I2C data read error"); + touchPanelDeInit(); + touchPanelInit(); return; } if (touchState.event == TE_NONE || touchState.event == TE_UP || @@ -779,7 +790,7 @@ extern "C" void TOUCH_INT_EXTI_IRQHandler1(void) // on touch turn the light on resetBacklightTimeout(); } - touchEventOccured = 1; + touchEventOccured = true; EXTI_ClearITPendingBit(TOUCH_INT_EXTI_LINE1); } } diff --git a/radio/src/targets/horus/tp_gt911.h b/radio/src/targets/horus/tp_gt911.h index 1a3371d31..b8f59677f 100644 --- a/radio/src/targets/horus/tp_gt911.h +++ b/radio/src/targets/horus/tp_gt911.h @@ -22,7 +22,7 @@ #define HAS_TOUCH_PANEL() touchGT911Flag == true -extern uint8_t touchGT911Flag; +extern bool touchGT911Flag; extern bool touchPanelInit(); void touchPanelRead(); From 8c7f3cecec21c5b541f462d87c18736bcaa7336c Mon Sep 17 00:00:00 2001 From: rotorman Date: Sat, 10 Jul 2021 19:05:23 +0200 Subject: [PATCH 2/4] * removed red LED * added GT911 fw version and hiccup cound output to analogs page * changed I2C to 400 kHz * changed X Y threshold to 1 * added trace output * fixed bool / uint8_t errors --- radio/src/gui/colorlcd/radio_diaganas.cpp | 10 +- radio/src/targets/horus/hal.h | 2 +- radio/src/targets/horus/tp_gt911.cpp | 140 ++++++++++++++++++---- radio/src/targets/horus/tp_gt911.h | 2 + radio/src/targets/nv14/touch_driver.cpp | 2 +- 5 files changed, 132 insertions(+), 24 deletions(-) diff --git a/radio/src/gui/colorlcd/radio_diaganas.cpp b/radio/src/gui/colorlcd/radio_diaganas.cpp index 3b24c3cd6..4de2b94d1 100644 --- a/radio/src/gui/colorlcd/radio_diaganas.cpp +++ b/radio/src/gui/colorlcd/radio_diaganas.cpp @@ -49,7 +49,7 @@ class RadioAnalogsDiagsWindow: public Window { } #if defined(HARDWARE_TOUCH) - constexpr coord_t y = MENU_CONTENT_TOP + 6 * FH; + constexpr coord_t y = MENU_CONTENT_TOP + 5 * FH; if (touchState.event != TE_NONE && touchState.event != TE_SLIDE_END) { coord_t x = dc->drawText(MENUS_MARGIN_LEFT, y, STR_TOUCH_PANEL); @@ -59,6 +59,14 @@ class RadioAnalogsDiagsWindow: public Window { dc->drawLine(touchState.x - 10, touchState.y - 8 - parent->top(), touchState.x + 10, touchState.y + 8 - parent->top(), SOLID, 0); dc->drawLine(touchState.x - 10, touchState.y + 8 - parent->top(), touchState.x + 10, touchState.y - 8- parent->top(), SOLID, 0); } +#if !defined(SIMU) + constexpr coord_t y1 = MENU_CONTENT_TOP + 6 * FH; + constexpr coord_t x1 = MENUS_MARGIN_LEFT; + dc->drawText(x1, y1, "Touch GT911 FW ver:"); + dc->drawNumber(x1 + 150, y1, touchGT911fwver, LEFT, 4); + dc->drawText(x1 + 200, y1, "Hiccups:"); + dc->drawNumber(x1 + 260, y1, touchGT911hiccups, LEFT, 5); +#endif #endif }; diff --git a/radio/src/targets/horus/hal.h b/radio/src/targets/horus/hal.h index cc12222fa..8d7be0da5 100644 --- a/radio/src/targets/horus/hal.h +++ b/radio/src/targets/horus/hal.h @@ -728,7 +728,7 @@ #define I2C_SCL_GPIO_PinSource GPIO_PinSource8 #define I2C_SDA_GPIO_PinSource GPIO_PinSource9 #endif -#define I2C_SPEED 100000 +#define I2C_SPEED 400000 // Haptic #define HAPTIC_PWM diff --git a/radio/src/targets/horus/tp_gt911.cpp b/radio/src/targets/horus/tp_gt911.cpp index 6b9823dd9..3bd973c24 100644 --- a/radio/src/targets/horus/tp_gt911.cpp +++ b/radio/src/targets/horus/tp_gt911.cpp @@ -39,9 +39,9 @@ const uint8_t TOUCH_GT911_Cfg[] = { 0x50, // 0x8053 Screen touch level 0x3C, // 0x8054 Screen touch leave 0x03, // 0x8055 Low power control - 0x05, // 0x8056 Refresh rate - 0x00, // 0x8057 X threshold - 0x00, // 0x8058 Y threshold + 0x0F, // 0x8056 Refresh rate + 0x01, // 0x8057 X threshold + 0x01, // 0x8058 Y threshold 0x00, // 0x8059 Reserved 0x00, // 0x805A Reserved 0x00, // 0x805B Space (top, bottom) @@ -231,8 +231,8 @@ const uint8_t TOUCH_GT911_Cfg[] = 0x3C, // 0x8054 Screen touch leave 0x03, // 0x8055 Low power control 0x0F, // 0x8056 Refresh rate - 0x0A, // 0x8057 X threshold - 0x0A, // 0x8058 Y threshold + 0x01, // 0x8057 X threshold + 0x01, // 0x8058 Y threshold 0x00, // 0x8059 Reserved 0x00, // 0x805A Reserved 0x11, // 0x805B Space (top, bottom) @@ -404,8 +404,10 @@ const uint8_t TOUCH_GT911_Cfg[] = #endif bool touchGT911Flag = false; -volatile bool touchEventOccured = false; +volatile static bool touchEventOccured = false; struct TouchData touchData; +uint16_t touchGT911fwver = 0; +uint16_t touchGT911hiccups = 0; static void TOUCH_AF_ExtiStop(void) { @@ -484,6 +486,8 @@ void TOUCH_AF_INT_Change(void) void I2C_Init() { + TRACE("I2C Init"); + I2C_DeInit(I2C); GPIO_InitTypeDef GPIO_InitStructure; @@ -529,33 +533,55 @@ bool I2C_WaitEventCleared(uint32_t event) uint8_t I2C_GT911_WriteRegister(uint16_t reg, uint8_t * buf, uint8_t len) { if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) + { + TRACE("I2C WRITE ERROR: busy timeout"); return false; + } I2C_GenerateSTART(I2C, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) + { + TRACE("I2C WRITE ERROR: could not issue start"); return false; + } I2C_Send7bitAddress(I2C, GT_CMD_WR, I2C_Direction_Transmitter); if (!I2C_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) + { + TRACE("I2C WRITE ERROR: could not send device address"); return false; + } I2C_SendData(I2C, (uint8_t)((reg & 0xFF00) >> 8)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) + { + TRACE("I2C WRITE ERROR: could not send register high address"); return false; + } + I2C_SendData(I2C, (uint8_t)(reg & 0x00FF)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) + { + TRACE("I2C WRITE ERROR: could not send register low address"); return false; + } /* While there is data to be written */ while (len--) { I2C_SendData(I2C, *buf); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) + { + TRACE("I2C WRITE ERROR: could not send data with %u bytes remaining", len+1 ); return false; + } buf++; } if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) + { + TRACE("I2C WRITE ERROR: waiting for BTF failed."); return false; + } I2C_GenerateSTOP(I2C, ENABLE); return true; @@ -564,35 +590,61 @@ uint8_t I2C_GT911_WriteRegister(uint16_t reg, uint8_t * buf, uint8_t len) bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) { if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) + { + TRACE("I2C READ ERROR: busy timeout"); return false; + } I2C_GenerateSTART(I2C, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) + { + TRACE("I2C READ ERROR: could not issue first step start"); return false; + } I2C_Send7bitAddress(I2C, GT_CMD_WR, I2C_Direction_Transmitter); if (!I2C_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) + { + TRACE("I2C READ ERROR: could not send first step device address"); return false; + } I2C_SendData(I2C, (uint8_t)((reg & 0xFF00) >> 8)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) + { + TRACE("I2C READ ERROR: could not send register high address"); return false; + } + I2C_SendData(I2C, (uint8_t)(reg & 0x00FF)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) + { + TRACE("I2C READ ERROR: could not send register low address"); return false; + } - // see GP911 data sheet, chapter 6.1.c, page 12, diagram for reading data + // According to GP911 data sheet, repeated start is not listed, so we do full stop. + // See chapter 6.1.c, page 12, diagram for reading data I2C_GenerateSTOP(I2C, ENABLE); if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) + { + TRACE("I2C READ ERROR: timeout waiting for first stop"); return false; + } I2C_GenerateSTART(I2C, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) + { + TRACE("I2C READ ERROR: could not issue second step start"); return false; + } I2C_Send7bitAddress(I2C, GT_CMD_RD, I2C_Direction_Receiver); if (!I2C_WaitEvent(I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED)) + { + TRACE("I2C READ ERROR: could not send second step device address"); return false; + } if (len > 1) { I2C_AcknowledgeConfig(I2C, ENABLE); @@ -600,10 +652,13 @@ bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) while (len) { if (len == 1) { - I2C_AcknowledgeConfig(I2C, DISABLE); + I2C_AcknowledgeConfig(I2C, DISABLE); // Send NACK on last byte } if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_RECEIVED)) + { + TRACE("I2C READ ERROR: could not read data with %u bytes remaining", len ); return false; + } *buf++ = I2C_ReceiveData(I2C); len--; } @@ -612,18 +667,30 @@ bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) return true; } -void I2C_GT911_SendConfig(uint8_t mode) +bool I2C_GT911_SendConfig(void) { uint8_t buf[2]; uint8_t i = 0; buf[0] = 0; - buf[1] = mode; + buf[1] = 1; + bool bResult = true; + for (i = 0; i < sizeof(TOUCH_GT911_Cfg); i++) buf[0] += TOUCH_GT911_Cfg[i];//check sum buf[0] = (~buf[0]) + 1; - I2C_GT911_WriteRegister(GT_CFGS_REG, (uint8_t *) TOUCH_GT911_Cfg, sizeof(TOUCH_GT911_Cfg));// - I2C_GT911_WriteRegister(GT_CHECK_REG, buf, 2);//write checksum + if (!I2C_GT911_WriteRegister(GT_CFGS_REG, (uint8_t *) TOUCH_GT911_Cfg, sizeof(TOUCH_GT911_Cfg))) + { + TRACE("GT911 ERROR: write config failed"); + bResult = false; + } + + if (!I2C_GT911_WriteRegister(GT_CHECK_REG, buf, 2)) //write checksum + { + TRACE("GT911 ERROR: write config checksum failed"); + bResult = false; + } + return bResult; } void touchPanelDeInit(void) @@ -661,29 +728,55 @@ bool touchPanelInit(void) delay_ms(50); TRACE("Reading Touch registry"); - I2C_GT911_ReadRegister(GT_PID_REG, tmp, 4); + if (!I2C_GT911_ReadRegister(GT_PID_REG, tmp, 4)) + { + TRACE("GT911 ERROR: Product ID read failed"); + } if (strcmp((char *) tmp, "911") == 0) //ID==9147 { TRACE("GT911 chip detected"); tmp[0] = 0X02; - I2C_GT911_WriteRegister(GT_CTRL_REG, tmp, 1); - I2C_GT911_ReadRegister(GT_CFGS_REG, tmp, 1); + if (!I2C_GT911_WriteRegister(GT_CTRL_REG, tmp, 1)) + { + TRACE("GT911 ERROR: write to control register failed"); + } + if (!I2C_GT911_ReadRegister(GT_CFGS_REG, tmp, 1)) + { + TRACE("GT911 ERROR: configration register read failed"); + } - TRACE("Chip config Ver:%x\r\n", tmp[0]); + TRACE("Chip config Ver:%x", tmp[0]); if (tmp[0] <= GT911_CFG_NUMER) //Config ver { TRACE("Sending new config %d", GT911_CFG_NUMER); - I2C_GT911_SendConfig(1); + if (!I2C_GT911_SendConfig()) + { + TRACE("GT911 ERROR: sending configration failed"); + } + } + + if (!I2C_GT911_ReadRegister(GT911_FIRMWARE_VERSION_REG, tmp, 2)) + { + TRACE("GT911 ERROR: reading firmware version failed"); + } + else + { + touchGT911fwver = (tmp[1] << 8) + tmp[0]; + TRACE("GT911 FW version: %u", touchGT911fwver); } delay_ms(10); tmp[0] = 0X00; - I2C_GT911_WriteRegister(GT_CTRL_REG, tmp, 1); //end reset + if (!I2C_GT911_WriteRegister(GT_CTRL_REG, tmp, 1)) //end reset + { + TRACE("GT911 ERROR: write to control register failed"); + } touchGT911Flag = true; TOUCH_AF_ExtiConfig(); + return true; } TRACE("GT911 chip NOT FOUND"); @@ -723,7 +816,8 @@ void touchPanelRead() uint32_t startReadStatus = RTOS_GET_MS(); do { if (!I2C_GT911_ReadRegister(GT911_READ_XY_REG, &state, 1)) { - ledRed(); + //ledRed(); + touchGT911hiccups++; TRACE("GT911 I2C read XY error"); touchPanelDeInit(); touchPanelInit(); @@ -744,7 +838,8 @@ void touchPanelRead() if (pointsCount > 0 && pointsCount <= GT911_MAX_TP) { if (!I2C_GT911_ReadRegister(GT911_READ_XY_REG + 1, touchData.data, pointsCount * sizeof(TouchPoint))) { - ledRed(); + //ledRed(); + touchGT911hiccups++; TRACE("GT911 I2C data read error"); touchPanelDeInit(); touchPanelInit(); @@ -778,7 +873,10 @@ void touchPanelRead() } uint8_t zero = 0; - I2C_GT911_WriteRegister(GT911_READ_XY_REG, &zero, 1); + if (!I2C_GT911_WriteRegister(GT911_READ_XY_REG, &zero, 1)) + { + TRACE("GT911 ERROR: clearing XY register failed"); + } TRACE("touch event = %s", event2str(touchState.event)); } diff --git a/radio/src/targets/horus/tp_gt911.h b/radio/src/targets/horus/tp_gt911.h index b8f59677f..cf0163712 100644 --- a/radio/src/targets/horus/tp_gt911.h +++ b/radio/src/targets/horus/tp_gt911.h @@ -23,6 +23,8 @@ #define HAS_TOUCH_PANEL() touchGT911Flag == true extern bool touchGT911Flag; +extern uint16_t touchGT911fwver; +extern uint16_t touchGT911hiccups; extern bool touchPanelInit(); void touchPanelRead(); diff --git a/radio/src/targets/nv14/touch_driver.cpp b/radio/src/targets/nv14/touch_driver.cpp index 72234dd0d..d93829674 100644 --- a/radio/src/targets/nv14/touch_driver.cpp +++ b/radio/src/targets/nv14/touch_driver.cpp @@ -21,7 +21,7 @@ #include "opentx.h" #include "touch_driver.h" -static bool touchEventOccured; +volatile static bool touchEventOccured; #define FT6x06_MAX_INSTANCE 1 From 49ae57d370e87155f47d57f591b3800d2a9444eb Mon Sep 17 00:00:00 2001 From: Raphael Coeffic Date: Sun, 11 Jul 2021 13:03:53 +0200 Subject: [PATCH 3/4] Take account of some corner cases in I2C multi-byte read See https://github.com/geoffreymbrown/STM32-Template/blob/master/Library/i2c.c#L39 and RM0090 p851-853. --- radio/src/targets/horus/tp_gt911.cpp | 106 +++++++++++++++++++++++---- 1 file changed, 93 insertions(+), 13 deletions(-) diff --git a/radio/src/targets/horus/tp_gt911.cpp b/radio/src/targets/horus/tp_gt911.cpp index 3bd973c24..ad7262924 100644 --- a/radio/src/targets/horus/tp_gt911.cpp +++ b/radio/src/targets/horus/tp_gt911.cpp @@ -512,6 +512,15 @@ void I2C_Init() GPIO_Init(I2C_GPIO, &GPIO_InitStructure); } +bool I2C_WaitFlag(uint32_t flag) +{ + uint32_t timeout = I2C_TIMEOUT_MAX; + while (!I2C_GetFlagStatus(I2C, flag)) { + if ((timeout--) == 0) return false; + } + return true; +} + bool I2C_WaitEvent(uint32_t event) { uint32_t timeout = I2C_TIMEOUT_MAX; @@ -632,6 +641,10 @@ bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) return false; } + // Enable Acknowledgement, clear POS flag + I2C_AcknowledgeConfig(I2C, ENABLE); + I2C_NACKPositionConfig(I2C, I2C_NACKPosition_Current); + I2C_GenerateSTART(I2C, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) { @@ -646,24 +659,91 @@ bool I2C_GT911_ReadRegister(u16 reg, uint8_t * buf, uint8_t len) return false; } - if (len > 1) { - I2C_AcknowledgeConfig(I2C, ENABLE); - } + if (len == 1) { + // Clear Ack bit + I2C_AcknowledgeConfig(I2C, DISABLE); - while (len) { - if (len == 1) { - I2C_AcknowledgeConfig(I2C, DISABLE); // Send NACK on last byte - } - if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_RECEIVED)) - { - TRACE("I2C READ ERROR: could not read data with %u bytes remaining", len ); + // EV6_1 -- must be atomic -- Clear ADDR, generate STOP + __disable_irq(); + (void) I2C->SR2; + I2C_GenerateSTOP(I2C,ENABLE); + __enable_irq(); + + // Receive data EV7 + if(!I2C_WaitFlag(I2C_FLAG_RXNE)) { + TRACE("I2C READ ERROR: timeout waiting for RxNE"); + I2C_Init(); return false; } + *buf++ = I2C_ReceiveData(I2C); - len--; + } + else if (len == 2) { + + // Set POS flag + I2C_NACKPositionConfig(I2C, I2C_NACKPosition_Next); + + // EV6_1 -- must be atomic and in this order + __disable_irq(); + (void) I2C->SR2; // Clear ADDR flag + I2C_AcknowledgeConfig(I2C, DISABLE); // Clear Ack bit + __enable_irq(); + + // EV7_3 -- Wait for BTF, program stop, read data twice + if (!I2C_WaitFlag(I2C_FLAG_BTF)) { + TRACE("I2C READ ERROR: timeout waiting for BTF"); + I2C_Init(); + return false; + } + + __disable_irq(); + I2C_GenerateSTOP(I2C,ENABLE); + *buf++ = I2C->DR; + __enable_irq(); + + *buf++ = I2C->DR; + } + else { + + (void) I2C->SR2; // Clear ADDR flag + while (len-- != 3) { + // EV7 -- cannot guarantee 1 transfer completion time, wait for BTF + // instead of RXNE + if (!I2C_WaitFlag(I2C_FLAG_BTF)) { + TRACE("I2C READ ERROR: timeout waiting for BTF"); + I2C_Init(); + return false; + } + + *buf++ = I2C_ReceiveData(I2C); + } + + // Data N-2 in DR, data N-1 in shift register, + // SCL stretched low until data N-2 is read + if (!I2C_WaitFlag(I2C_FLAG_BTF)) { + TRACE("I2C READ ERROR: timeout waiting for BTF"); + I2C_Init(); + return false; + } + + I2C_AcknowledgeConfig(I2C, DISABLE); // clear ack bit + *buf++ = I2C_ReceiveData(I2C); // receive byte N-2 + + // Wait for BTF, program stop, read data twice + if (!I2C_WaitFlag(I2C_FLAG_BTF)) { + TRACE("I2C READ ERROR: timeout waiting for BTF"); + I2C_Init(); + return false; + } + + __disable_irq(); + I2C_GenerateSTOP(I2C,ENABLE); + *buf++ = I2C->DR; + __enable_irq(); + + *buf++ = I2C->DR; } - I2C_GenerateSTOP(I2C, ENABLE); return true; } @@ -743,7 +823,7 @@ bool touchPanelInit(void) } if (!I2C_GT911_ReadRegister(GT_CFGS_REG, tmp, 1)) { - TRACE("GT911 ERROR: configration register read failed"); + TRACE("GT911 ERROR: configuration register read failed"); } TRACE("Chip config Ver:%x", tmp[0]); From 52acfcd20db157906b315449ce6bbc22ec5b2660 Mon Sep 17 00:00:00 2001 From: Raphael Coeffic Date: Sun, 11 Jul 2021 17:43:31 +0200 Subject: [PATCH 4/4] Quick & dirty polling mode (don't care about INT line) --- radio/src/targets/horus/tp_gt911.cpp | 6 +++--- radio/src/targets/horus/tp_gt911.h | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/radio/src/targets/horus/tp_gt911.cpp b/radio/src/targets/horus/tp_gt911.cpp index ad7262924..0802ba3f4 100644 --- a/radio/src/targets/horus/tp_gt911.cpp +++ b/radio/src/targets/horus/tp_gt911.cpp @@ -888,10 +888,10 @@ void touchPanelRead() { uint8_t state = 0; - if (!touchEventOccured) - return; + // if (!touchEventOccured) + // return; - touchEventOccured = false; + // touchEventOccured = false; uint32_t startReadStatus = RTOS_GET_MS(); do { diff --git a/radio/src/targets/horus/tp_gt911.h b/radio/src/targets/horus/tp_gt911.h index cf0163712..2a051e847 100644 --- a/radio/src/targets/horus/tp_gt911.h +++ b/radio/src/targets/horus/tp_gt911.h @@ -30,7 +30,7 @@ extern bool touchPanelInit(); void touchPanelRead(); bool touchPanelEventOccured(); -#define GT911_TIMEOUT 20 // 20ms +#define GT911_TIMEOUT 3 // 3ms #define GT911_MAX_TP 5 #define GT911_CFG_NUMER 0x6C