SvcCyttsp6_tsDriver.h
/**
* @file SvcCyttsp6_tsDriver.h
*
* @Date:2022-08-23
*
* @details contrl interface
*/
#ifndef __SVCCYTTSP6_TS_DRIVER_H_
#define __SVCCYTTSP6_TS_DRIVER_H_
#define IS_BOOTLOADER(hst_mode, reset_detect) \
((hst_mode) & 0x01 || (reset_detect) != 0)
#define IS_BOOTLOADER_IDLE(hst_mode, reset_detect) \
((hst_mode) & 0x01 && (reset_detect) & 0x01)
/* helpers */
#define GET_NUM_TOUCH_RECORDS(x) ((x) & 0x1F)
#define CY_BL_MAX_STATUS_SIZE 32
/* Communication bus values */
#define CY_DEFAULT_ADAP_MAX_XFER 512
#define CY_ADAP_MIN_XFER 64
/* DEVICE REGISTERS */
/* OP MODE REGISTERS */
#define CY_REG_BASE 0x00
/* DRIVER STATES */
enum cyttsp6_mode {
CY_MODE_UNKNOWN = 0,
CY_MODE_BOOTLOADER = (1 << 0),
CY_MODE_OPERATIONAL = (1 << 1),
CY_MODE_SYSINFO = (1 << 2),
CY_MODE_CAT = (1 << 3),
CY_MODE_STARTUP = (1 << 4),
CY_MODE_LOADER = (1 << 5),
CY_MODE_CHANGE_MODE = (1 << 6),
CY_MODE_CHANGED = (1 << 7),
CY_MODE_CMD_COMPLETE = (1 << 8),
};
enum cyttsp6_int_state {
CY_INT_NONE,
CY_INT_IGNORE = (1 << 0),
CY_INT_MODE_CHANGE = (1 << 1),
CY_INT_EXEC_CMD = (1 << 2),
CY_INT_AWAKE = (1 << 3),
};
enum cyttsp6_hst_mode_bits {
CY_HST_TOGGLE = (1 << 7),
CY_HST_MODE_CHANGE = (1 << 3),
CY_HST_DEVICE_MODE = (7 << 4),
CY_HST_OPERATE = (0 << 4),
CY_HST_SYSINFO = (1 << 4),
CY_HST_CAT = (2 << 4),
CY_HST_LOWPOW = (1 << 2),
CY_HST_SLEEP = (1 << 1),
CY_HST_RESET = (1 << 0),
};
enum cyttsp_cmd_bits {
CY_CMD_COMPLETE = (1 << 6),
};
struct cyttsp6_core_data {
enum cyttsp6_mode mode;
UINT32 int_status; // u
UINT8 heartbeat_count;
UINT8 xy_mode[128]; /* operational mode and status regs */
UINT8 *xy_data; /* operational touch regs */
};
/* Timeout in ms. */
#define CY_CORE_WAIT_SYSINFO_MODE_TIMEOUT 4000
#define CY_CORE_MODE_CHANGE_TIMEOUT 2000
/* TMA400 HOST SYNC BYTE */
#define CY_CMD_LDR_HOST_SYNC 0xFF
#define CY_START_OF_PACKET 0x01
#define CY_END_OF_PACKET 0x17
/* CMD */
enum cyttsp6_cmd_bl {
CY_CMD_LDR_VERIFY_CHKSUM = 0x31,
CY_CMD_LDR_ERASE_ROW = 0x34,
CY_CMD_LDR_SEND_DATA = 0x37,
CY_CMD_LDR_ENTER,
CY_CMD_LDR_PROG_ROW,
CY_CMD_LDR_VERIFY_ROW,
CY_CMD_LDR_EXIT,
CY_CMD_LDR_FAST_EXIT,
CY_CMD_LDR_INIT = 0x48,
};
#define CY_CMD_OFS 2
#define CY_REP_HDR_SIZE 19
#define CY_TCH_REC_SIZE 10
#define CY_REP_OFS 9
#define CY_TT_STAT_OFS 27
#define CY_MAX_TCHS 2
extern struct cyttsp6_core_data g_cd;
#define CYTTSP6_TS_DEVICE_ADDR (0x48U)
#define CYTTSP6_TP_RESET (GPIO_PIN_101)
#define CYTTSP6_TP_INT (GPIO_PIN_102)
UINT32 SvcCyttsp6DriverTask_Init(void);
#endif
SvcCyttsp6_tsDriver.c
/**
* @file SvcCyttsp6_tsDriver.c
*
* @author:lzh
*
* @Date:2022-08-23
*
* @Description: Cyttsp6 ts driver
*/
#include "AmbaGPIO.h"
#include "AmbaKAL.h"
#include "AmbaPrint.h"
#include "AmbaUtility.h"
#include "SvcWrap.h"
#include "SvcTask.h"
#include "SvcLog.h"
#include "SvcErrCode.h"
#include "SvcSysStat.h"
#include "AmbaI2C.h"
#include "SvcCyttsp6_tsDriver.h"
#define SVC_TP_DRV_TASK_CPU_BITS (0x1U)
#define TP_DRV_STACK_SIZE (0x100000U)
#define TP_DRV_STACK_PRI (SVC_TASK_LOWEST_PRIORITY - 14U)
#define SVC_LOG_TP_DRV_TASK "CyttspDrv"
/* Cyttsp irq */
#define SVC_CYTTSP_IRQ_TRIGGER (0x01U)
/* Cyttsp mode status */
#define SVC_CYTTSP_MODE_STATUS_BL (0x01U)
#define SVC_CYTTSP_MODE_STATUS_SYSINFO (0x02U)
#define SVC_CYTTSP_MODE_STATUS_CHANGE (0x04U)
struct cyttsp6_core_data g_cd;
typedef struct {
SVC_TASK_CTRL_s TpDrvTask;
SVC_TASK_CTRL_s TpIrqTask;
AMBA_KAL_EVENT_FLAG_t IrqEventFlg;
char IrqEventFlgName[32U];
AMBA_KAL_EVENT_FLAG_t StsEventFlg;
char StsEventFlgName[32U];
} SVC_CYTTSP6_DRV_TSK_s;
static SVC_CYTTSP6_DRV_TSK_s CyttspDrv GNU_SECTION_NOZEROINIT;
static UINT8 ldr_exit[] = {
CY_CMD_LDR_HOST_SYNC, CY_START_OF_PACKET, CY_CMD_LDR_EXIT, 0x00, 0x00,
0x4F, 0x6D, CY_END_OF_PACKET
};
static UINT8 ldr_fast_exit[] = {
CY_CMD_LDR_HOST_SYNC, CY_START_OF_PACKET, CY_CMD_LDR_FAST_EXIT,
0x00, 0x00, 0xC3, 0x68, CY_END_OF_PACKET
};
static UINT32 Amba_cyttsp6_adap_read(UINT8 addr,void *buf, UINT32 size);
static UINT32 Amba_cyttsp6_adap_write(UINT8 addr,void *buf, UINT32 size);
/*******************************************************************************/
static UINT32 Amba_cyttsp6_adap_read(UINT8 addr,void *buf, UINT32 size)
{
UINT32 RetVal = SVC_OK;
UINT32 MasterId = AMBA_I2C_CHANNEL3; // i2c-3
UINT32 SpeedMode = AMBA_I2C_SPEED_FAST; //
UINT8 TxData = 0;
UINT8* RxData = (UINT8*)buf;
UINT32 TxSize;
AMBA_I2C_TRANSACTION_s I2cTxCfg = {0};
AMBA_I2C_TRANSACTION_s I2cRxCfg = {0};
TxData = addr;
I2cTxCfg.SlaveAddr = CYTTSP6_TS_DEVICE_ADDR; // CYTTSP6 device address
I2cTxCfg.DataSize = 1U;
I2cTxCfg.pDataBuf = &TxData;
I2cRxCfg.SlaveAddr = CYTTSP6_TS_DEVICE_ADDR + 1U; // CYTTSP6 read device address
I2cRxCfg.DataSize = size;
I2cRxCfg.pDataBuf = RxData;
RetVal = AmbaI2C_MasterReadAfterWrite(MasterId, SpeedMode, 1U, &I2cTxCfg, &I2cRxCfg, &TxSize, 1000U);
if (RetVal != I2C_ERR_NONE){
SvcLog_NG(SVC_LOG_TP_DRV_TASK, "Read Cyttsp register[0x%x] failed!!", addr, 0);
}
return RetVal;
}
static UINT32 Amba_cyttsp6_adap_write(UINT8 addr,void *buf, UINT32 size)
{
UINT32 RetVal = SVC_OK;
UINT32 MasterId = AMBA_I2C_CHANNEL3; // i2c-3
UINT32 SpeedMode = AMBA_I2C_SPEED_FAST; //
UINT32 TxSize;
UINT8 TxDataBuf[size+1];
AMBA_I2C_TRANSACTION_s I2cConfig = {0};
I2cConfig.SlaveAddr = CYTTSP6_TS_DEVICE_ADDR;
I2cConfig.DataSize = size + 1U;
I2cConfig.pDataBuf = TxDataBuf;
TxDataBuf[0] = (UINT8) addr;
AmbaWrap_memcpy(&TxDataBuf[1], buf, size);
RetVal = AmbaI2C_MasterWrite(MasterId, SpeedMode,
&I2cConfig, &TxSize, 1000U);
if (RetVal != I2C_ERR_NONE){
SvcLog_NG(SVC_LOG_TP_DRV_TASK, "Write Cyttsp register[0x%x] failed!!", addr, 0);
}
return RetVal;
}
static UINT32 Amba_Cyttsp6_Exit_Bootloader(struct cyttsp6_core_data *cd)
{
UINT8 *exit_cmd;
UINT32 exit_cmd_size;
UINT32 RetVal;
cd->int_status &= ~CY_INT_IGNORE;
cd->int_status |= CY_INT_MODE_CHANGE;
if(0)
{
exit_cmd = ldr_fast_exit;
exit_cmd_size = sizeof(ldr_fast_exit);
} else {
exit_cmd = ldr_exit;
exit_cmd_size = sizeof(ldr_exit);
}
RetVal = Amba_cyttsp6_adap_write( CY_REG_BASE, exit_cmd, exit_cmd_size);
if (RetVal != SVC_OK)
{
AmbaPrint_PrintInt5("==== >_exit_bootloader:cyttsp6_adap_write err\r\n",0U,0U,0U,0U,0U);
}
return RetVal;
}
static UINT32 Amba_Cyttsp6_Mode_Set(struct cyttsp6_core_data *cd, int new_mode)
{
UINT32 RetVal = SVC_OK;
UINT8 new_dev_mode;
UINT8 mode;
UINT32 ActualFlag;
switch (new_mode) {
case CY_MODE_OPERATIONAL:
new_dev_mode = CY_HST_OPERATE;
break;
case CY_MODE_SYSINFO:
new_dev_mode = CY_HST_SYSINFO;
break;
case CY_MODE_CAT:
new_dev_mode = CY_HST_CAT;
break;
default:
AmbaPrint_PrintInt5("set_mode:invalid mode: %2x(%d)\r\n",new_mode, new_mode,0U,0U,0U);
return SVC_NG;
}
/* change mode */
RetVal = Amba_cyttsp6_adap_read( CY_REG_BASE, &mode, sizeof(mode));
if ( SVC_OK != RetVal ) {
AmbaPrint_PrintInt5("set_mode:Fail read mode RetVal=0x%x\r\n",RetVal,0U,0U,0U,0U);
goto exit;
}
/* Clear device mode bits and set to new mode */
mode &= ~CY_HST_DEVICE_MODE;
mode |= new_dev_mode | CY_HST_MODE_CHANGE;
cd->int_status |= CY_INT_MODE_CHANGE;
RetVal = Amba_cyttsp6_adap_write( CY_REG_BASE, &mode, sizeof(mode));
if ( SVC_OK != RetVal ) {
AmbaPrint_PrintInt5("Fail write mode change RetVal=0x%x\r\n",RetVal,0U,0U,0U,0U);
goto exit;
}
/* wait for mode change done interrupt */
AmbaPrint_PrintInt5("wait new_mode[%d] change...\r\n",new_mode,0U,0U,0U,0U);
RetVal = AmbaKAL_EventFlagGet(&(CyttspDrv.StsEventFlg),
SVC_CYTTSP_MODE_STATUS_CHANGE,
AMBA_KAL_FLAGS_ALL,
AMBA_KAL_FLAGS_CLEAR_NONE,
&ActualFlag,
CY_CORE_MODE_CHANGE_TIMEOUT);
if(SVC_OK != RetVal){
AmbaPrint_PrintInt5("Amba_Cyttsp6_Mode_Set:Wait new mode change timeout!!\r\n",0U,0U,0U,0U,0U);
}else{
AmbaKAL_EventFlagClear(&(CyttspDrv.StsEventFlg), 0xFFFFFFFFU);
}
exit:
return RetVal;
}
static void Amba_cyttsp6_parse_mode(UINT8 mode,enum cyttsp6_mode *cur_mode)
{
switch (mode & CY_HST_DEVICE_MODE)
{
case CY_HST_OPERATE:
*cur_mode = CY_MODE_OPERATIONAL;
break;
case CY_HST_CAT:
*cur_mode = CY_MODE_CAT;
break;
case CY_HST_SYSINFO:
*cur_mode = CY_MODE_SYSINFO;
(void)AmbaKAL_EventFlagSet(&(CyttspDrv.StsEventFlg), SVC_CYTTSP_MODE_STATUS_SYSINFO);
break;
default:
*cur_mode = CY_MODE_UNKNOWN;
AmbaPrint_PrintInt5("cyttsp6_parse_mode:unknown HST mode 0x%2x\r\n",mode,0U,0U,0U,0U);
break;
}
}
static UINT32 Amba_cyttsp6_wait_sysinfo_mode(void)
{
UINT32 RetVal = SVC_OK;
UINT32 ActualFlag;
AmbaPrint_PrintInt5("wait sysinfo...\r\n",0U,0U,0U,0U,0U);
RetVal = AmbaKAL_EventFlagGet(&(CyttspDrv.StsEventFlg),
SVC_CYTTSP_MODE_STATUS_SYSINFO,
AMBA_KAL_FLAGS_ALL,
AMBA_KAL_FLAGS_CLEAR_NONE,
&ActualFlag,
CY_CORE_WAIT_SYSINFO_MODE_TIMEOUT);
if(SVC_OK != RetVal){
AmbaPrint_PrintInt5("Amba_cyttsp6_wait_sysinfo_mode:Wait sysinfo mode timeout!!\r\n",0U,0U,0U,0U,0U);
}else{
AmbaKAL_EventFlagClear(&(CyttspDrv.StsEventFlg), 0xFFFFFFFFU);
}
return RetVal;
}
UINT32 Amba_cyttsp6_startup(struct cyttsp6_core_data *cd)
{
UINT32 RetVal;
cd->xy_data = &cd->xy_mode[28];
/* exit bl into sysinfo mode */
RetVal = Amba_Cyttsp6_Exit_Bootloader(cd);
if (SVC_OK != RetVal) {
AmbaPrint_PrintInt5("cyttsp6_startup:Fail exit bootloader RetVal=%d\r\n",RetVal,0U,0U,0U,0U);
return RetVal;
}
RetVal = Amba_cyttsp6_wait_sysinfo_mode();
if(SVC_OK != RetVal){
AmbaPrint_PrintInt5("cyttsp6_startup:Fail switch to sysinfo mode, RetVal=%d\r\n",RetVal,0U,0U,0U,0U);
goto exit_lock;
}
RetVal = Amba_Cyttsp6_Mode_Set(cd, CY_MODE_OPERATIONAL);
if (SVC_OK != RetVal) {
AmbaPrint_PrintInt5("cyttsp6_startup:Fail set mode to Operational mode, RetVal=%d\r\n",RetVal,0U,0U,0U,0U);
goto exit_lock;
}
exit_lock:
return RetVal;
}
static UINT32 Amba_cyttsp6_handshake_(UINT8 mode)
{
UINT8 cmd = mode ^ CY_HST_TOGGLE;
UINT32 RetVal = SVC_OK;
if (mode & CY_HST_MODE_CHANGE) {
AmbaPrint_PrintInt5("cyttsp6_handshake_:Host mode change bit set, NO handshake\r\n",0U,0U,0U,0U,0U);
return SVC_NG;
}
RetVal = Amba_cyttsp6_adap_write(CY_REG_BASE, &cmd, sizeof(cmd));
if (RetVal != SVC_OK)
AmbaPrint_PrintInt5("cyttsp6_handshake_:bus write fail on handshake (ret=%d)\r\n",RetVal,0U,0U,0U,0U);
return RetVal;
}
static UINT32 Amba_Cyttsp6_LoadStatusAndTouchRegs(struct cyttsp6_core_data *cd,UINT8 optimize)
{
UINT32 RetVal = SVC_OK;
UINT32 first_read_len;
UINT32 second_read_off;
INT32 num_read_rec;
UINT8 num_cur_rec;
UINT8 rep_len;
UINT8 tt_stat;
UINT8 i = 0;
first_read_len = CY_REP_HDR_SIZE; //si->si_ofs.rep_hdr_size;
/* Read one touch record additionally */
if (optimize)
first_read_len += CY_TCH_REC_SIZE; //si->si_ofs.tch_rec_size;
RetVal = Amba_cyttsp6_adap_read( CY_REP_OFS /*si->si_ofs.rep_ofs*/,
&cd->xy_mode[CY_REP_OFS/*si->si_ofs.rep_ofs*/], first_read_len);
if ( SVC_OK != RetVal ) {
AmbaPrint_PrintInt5("cyttsp6_load_status_and_touch_regs_:reading touch record failed RetVal=%d\r\n",RetVal,0U,0U,0U,0U);
return RetVal;
}
rep_len = cd->xy_mode[CY_REP_OFS/*si->si_ofs.rep_ofs*/];
tt_stat = cd->xy_mode[CY_TT_STAT_OFS /*si->si_ofs.tt_stat_ofs*/];
num_cur_rec = GET_NUM_TOUCH_RECORDS(tt_stat);
if (rep_len == 0 && num_cur_rec > 0)
{
AmbaPrint_PrintInt5("cyttsp6_load_status_and_touch_regs_:report length error rep_len=%d num_rec=%d\r\n",rep_len,num_cur_rec,0U,0U,0U);
return SVC_NG;
}
if (num_cur_rec > CY_MAX_TCHS /*si->si_ofs.max_tchs*/)
{
num_cur_rec = CY_MAX_TCHS /*si->si_ofs.max_tchs*/;
}
num_read_rec = num_cur_rec;
second_read_off = CY_TT_STAT_OFS + 1; //si->si_ofs.tt_stat_ofs + 1;
if (optimize)
{
num_read_rec--;
second_read_off += CY_TCH_REC_SIZE; //si->si_ofs.tch_rec_size;
}
if (num_read_rec <= 0)
{
goto exit_print;
}
RetVal = Amba_cyttsp6_adap_read(second_read_off,&cd->xy_mode[second_read_off],num_read_rec * CY_TCH_REC_SIZE /*si->si_ofs.tch_rec_size*/);
if ( SVC_OK != RetVal ) {
AmbaPrint_PrintInt5("cyttsp6_load_status_and_touch_regs_:read fail on touch regs RetVal=%d\r\n",RetVal,0U,0U,0U,0U);
return RetVal;
}
// Send data
AmbaPrint_PrintInt5("Amba_cyttsp6_adap_read:num_read_rec=%d\r\n",num_read_rec,0U,0U,0U,0U);
for(i = 0; i< num_read_rec; i++)
{
AmbaPrint_PrintInt5("Amba_cyttsp6_adap_read:Resolution = %d x %d\n",cd->xy_mode[29+i*10] | (cd->xy_mode[28+i*10] << 8),
cd->xy_mode[31+i*10] | (cd->xy_mode[30+i*10] << 8),0U,0U,0U);
AmbaPrint_PrintInt5("Amba_cyttsp6_adap_read:P T MAJ = 0x%x 0x%x 0x%x \n",cd->xy_mode[32+i*10],cd->xy_mode[33+i*10],cd->xy_mode[36+i*10],0U,0U);
#if 0
I2C_SendBuf[I2CSendFillNum].buf[1+i*7] = cd->xy_mode[28+i*10];
I2C_SendBuf[I2CSendFillNum].buf[2+i*7] = cd->xy_mode[29+i*10];//X
I2C_SendBuf[I2CSendFillNum].buf[3+i*7] = cd->xy_mode[30+i*10];
I2C_SendBuf[I2CSendFillNum].buf[4+i*7] = cd->xy_mode[31+i*10];//Y
I2C_SendBuf[I2CSendFillNum].buf[5+i*7] = cd->xy_mode[32+i*10];//P
I2C_SendBuf[I2CSendFillNum].buf[6+i*7] = cd->xy_mode[33+i*10];//T
I2C_SendBuf[I2CSendFillNum].buf[7+i*7] = cd->xy_mode[36+i*10];//MAJ
#endif
}
exit_print:
return RetVal;
}
UINT32 Amba_cyttsp6_irq(struct cyttsp6_core_data *cd)
{
enum cyttsp6_mode cur_mode;
UINT8 cmd_ofs = CY_CMD_OFS;//cd->sysinfo.si_ofs.cmd_ofs;
UINT8 command_complete = 0;
UINT8 mode[3];
UINT32 RetVal;
RetVal = Amba_cyttsp6_adap_read(CY_REG_BASE, mode, sizeof(mode));
if (RetVal != SVC_OK)
{
AmbaPrint_PrintInt5("cyttsp6_irq:cyttsp6_adap_read err RetVal = 0x%x\r\n",RetVal,0U,0U,0U,0U);
goto cyttsp6_irq_exit;
}
if (IS_BOOTLOADER(mode[0], mode[1]))
{
AmbaPrint_PrintInt5("cyttsp6_irq:IS_BOOTLOADER\r\n",0U,0U,0U,0U,0U);
cur_mode = CY_MODE_BOOTLOADER;
/* switch to bootloader */
if (cd->mode != CY_MODE_BOOTLOADER)
{
}
/* catch operation->bl glitch */
if ((cd->mode != CY_MODE_BOOTLOADER) && (cd->mode != CY_MODE_UNKNOWN))
{
/* Incase startup_state, do not let startup_() */
cd->mode = CY_MODE_UNKNOWN;
AmbaPrint_PrintInt5("cyttsp6_irq:CY_MODE_UNKNOWN\r\n",0U,0U,0U,0U,0U);
goto cyttsp6_irq_exit;
}
/* Recover if stuck in bootloader idle mode */
if (cd->mode == CY_MODE_BOOTLOADER)
{
if (IS_BOOTLOADER_IDLE(mode[0], mode[1]))
{
if (cd->heartbeat_count > 3)
{
cd->heartbeat_count = 0;
/* exit bl into sysinfo mode */
RetVal = Amba_Cyttsp6_Exit_Bootloader(cd);
if (RetVal != SVC_OK)
{
AmbaPrint_PrintInt5("cyttsp6_startup:_exit_bootloader err\r\n",0U,0U,0U,0U,0U);
}
goto cyttsp6_irq_exit;
}
cd->heartbeat_count++;
}
}
cd->mode = cur_mode;
/* Signal bootloader heartbeat heard */
(void)AmbaKAL_EventFlagSet(&(CyttspDrv.StsEventFlg), SVC_CYTTSP_MODE_STATUS_BL);
goto cyttsp6_irq_exit;
}
Amba_cyttsp6_parse_mode(mode[0], &cur_mode);
/* Check whether this IRQ should be ignored (internal) */
if (cd->int_status & CY_INT_IGNORE)
{
}
/* Check for wake up interrupt */
if (cd->int_status & CY_INT_AWAKE)
{
cd->int_status &= ~CY_INT_AWAKE;
//wake_up(&cd->wait_q);
goto cyttsp6_irq_handshake;
}
/* Expecting mode change interrupt */
if ((cd->int_status & CY_INT_MODE_CHANGE) && ((mode[0] & CY_HST_MODE_CHANGE) == 0))
{
cd->int_status &= ~CY_INT_MODE_CHANGE;
cd->mode = cur_mode;
//wake_up(&cd->wait_q);
(void)AmbaKAL_EventFlagSet(&(CyttspDrv.StsEventFlg), SVC_CYTTSP_MODE_STATUS_CHANGE);
goto cyttsp6_irq_handshake;
}
/* compare current core mode to current device mode */
if (((mode[0] & CY_HST_MODE_CHANGE) == 0) && cd->mode != cur_mode)
{
AmbaPrint_PrintInt5("cyttsp6_irq:%d %d->%d int:%s\r\n",cd->mode,cur_mode,cd->int_status,0U,0U);
goto cyttsp6_irq_exit;
}
/* Expecting command complete interrupt */
if ((cd->int_status & CY_INT_EXEC_CMD)
&& mode[cmd_ofs] & CY_CMD_COMPLETE)
{
command_complete = 1;
cd->int_status &= ~CY_INT_EXEC_CMD;
//wake_up(&cd->wait_q);
/*
* It is possible to receive a single interrupt for
* command complete and touch/button status report.
* Continue processing for a possible status report.
*/
}
if (!cd->xy_mode)
{
AmbaPrint_PrintInt5("cyttsp6_irq_handshake3\r\n",0U,0U,0U,0U,0U);
goto cyttsp6_irq_handshake;
}
/* Copy the mode registers */
AmbaWrap_memcpy(cd->xy_mode, mode, sizeof(mode));
/* This should be status report, read status and touch regs */
if (cd->mode == CY_MODE_OPERATIONAL)
{
RetVal = Amba_Cyttsp6_LoadStatusAndTouchRegs(cd, command_complete);
if (RetVal != SVC_OK)
AmbaPrint_PrintInt5("cyttsp6_irq:fail read mode/touch regs RetVal=%d\r\n",RetVal,0U,0U,0U,0U);
}
cyttsp6_irq_handshake:
/* handshake the event */
RetVal = Amba_cyttsp6_handshake_( mode[0]);
if (RetVal != SVC_OK)
AmbaPrint_PrintInt5("cyttsp6_irq:Fail handshake mode=0x%2x RetVal=%d\r\n",mode[0],RetVal,0U,0U,0U);
cyttsp6_irq_exit:
return RetVal;
}
static void *SvcTpIrqTaskEntry(void *EntryArg)
{
UINT32 ActualFlag;
AmbaMisra_TouchUnused(EntryArg);
while(1){
if(SVC_OK == AmbaKAL_EventFlagGet(&(CyttspDrv.IrqEventFlg),
SVC_CYTTSP_IRQ_TRIGGER,
AMBA_KAL_FLAGS_ALL,
AMBA_KAL_FLAGS_CLEAR_NONE,
&ActualFlag,
AMBA_KAL_WAIT_FOREVER)){
AmbaKAL_EventFlagClear(&(CyttspDrv.IrqEventFlg), 0xFFFFFFFFU);
Amba_cyttsp6_irq(&g_cd);
}
}
return NULL;
}
void Cyttsp_TP_Isr(UINT32 GpioPinID, UINT32 UserArg)
{
AmbaMisra_TouchUnused(&GpioPinID);
AmbaMisra_TouchUnused(&UserArg);
(void)AmbaKAL_EventFlagSet(&(CyttspDrv.IrqEventFlg), SVC_CYTTSP_IRQ_TRIGGER);
}
static void SvcCyttsp_tpReset(void)
{
/* tp reset */
(void)AmbaGPIO_SetFuncGPO(CYTTSP6_TP_RESET, AMBA_GPIO_LEVEL_LOW);
AmbaKAL_TaskSleep(10U);
(void)AmbaGPIO_SetFuncGPO(CYTTSP6_TP_RESET, AMBA_GPIO_LEVEL_HIGH);
}
static void SvcCyttsp_tpIntRegister(void)
{
AmbaGPIO_IntSetType(CYTTSP6_TP_INT,GPIO_INT_FALLING_EDGE_TRIGGER);
AmbaGPIO_IntHookHandler(CYTTSP6_TP_INT, &Cyttsp_TP_Isr, 0U);
//AmbaGPIO_IntEnable(CYTTSP6_TP_INT);
}
static void *SvcTpDrvTaskEntry(void *EntryArg)
{
UINT32 RetVal = SVC_OK;
UINT8 RetryCnt = 0;
AmbaMisra_TouchUnused(EntryArg);
SvcCyttsp_tpIntRegister();
while(1){
Retry:
AmbaGPIO_IntDisable(CYTTSP6_TP_INT);
SvcCyttsp_tpReset();
AmbaKAL_TaskSleep(100U);
SvcCyttsp_tpIntRegister();
AmbaGPIO_IntEnable(CYTTSP6_TP_INT);
RetVal = Amba_cyttsp6_startup(&g_cd);
if( (SVC_OK != RetVal) && ( RetryCnt < 3 ) ){
RetryCnt++;
AmbaKAL_TaskSleep(500U);
goto Retry;
}else{
break;
}
}
return NULL;
}
UINT32 SvcCyttsp6DriverTask_Init(void)
{
UINT32 RetVal = SVC_OK;
static UINT8 TpDrvTaskStack[TP_DRV_STACK_SIZE] GNU_SECTION_NOZEROINIT;
static UINT8 TpIrqTaskStack[TP_DRV_STACK_SIZE] GNU_SECTION_NOZEROINIT;
AmbaWrap_memset(&CyttspDrv, 0, sizeof(CyttspDrv));
/* Create cyttsp irq event flag */
AmbaUtility_StringAppend(CyttspDrv.IrqEventFlgName, (UINT32)sizeof(CyttspDrv.IrqEventFlgName), "TpIrqEventFlag");
RetVal = AmbaKAL_EventFlagCreate(&(CyttspDrv.IrqEventFlg), CyttspDrv.IrqEventFlgName);
if (RetVal != SVC_OK) {
SvcLog_NG(SVC_LOG_TP_DRV_TASK, "Failure to initial Cyttsp driver task - create event flag fail!", 0U, 0U);
} else {
RetVal = AmbaKAL_EventFlagClear(&(CyttspDrv.IrqEventFlg), 0xFFFFFFFFU);
}
/* Create cyttsp mode status event flag */
AmbaUtility_StringAppend(CyttspDrv.StsEventFlgName, (UINT32)sizeof(CyttspDrv.StsEventFlgName), "TpStsEventFlag");
RetVal = AmbaKAL_EventFlagCreate(&(CyttspDrv.StsEventFlg), CyttspDrv.StsEventFlgName);
if (RetVal != SVC_OK) {
SvcLog_NG(SVC_LOG_TP_DRV_TASK, "Failure to initial Cyttsp driver task - create event flag fail!", 0U, 0U);
} else {
RetVal = AmbaKAL_EventFlagClear(&(CyttspDrv.StsEventFlg), 0xFFFFFFFFU);
}
if (SVC_OK == RetVal) {
CyttspDrv.TpIrqTask.Priority = TP_DRV_STACK_PRI;
CyttspDrv.TpIrqTask.EntryFunc = SvcTpIrqTaskEntry;
CyttspDrv.TpIrqTask.EntryArg = 0U;
CyttspDrv.TpIrqTask.StackSize = TP_DRV_STACK_SIZE;
CyttspDrv.TpIrqTask.pStackBase = TpIrqTaskStack;
CyttspDrv.TpIrqTask.CpuBits = SVC_TP_DRV_TASK_CPU_BITS;
RetVal = SvcTask_Create("TpIrqTask", &CyttspDrv.TpIrqTask);
if (RetVal != SVC_OK) {
SvcLog_NG(SVC_LOG_TP_DRV_TASK, "SvcCyttsp6DriverTask_Init err, SvcTask_Create failed with 0x%x", RetVal, 0U);
}
}
if (SVC_OK == RetVal) {
CyttspDrv.TpDrvTask.Priority = TP_DRV_STACK_PRI;
CyttspDrv.TpDrvTask.EntryFunc = SvcTpDrvTaskEntry;
CyttspDrv.TpDrvTask.EntryArg = 0U;
CyttspDrv.TpDrvTask.StackSize = TP_DRV_STACK_SIZE;
CyttspDrv.TpDrvTask.pStackBase = TpDrvTaskStack;
CyttspDrv.TpDrvTask.CpuBits = SVC_TP_DRV_TASK_CPU_BITS;
RetVal = SvcTask_Create("TpDrvTask", &CyttspDrv.TpDrvTask);
if (RetVal != SVC_OK) {
SvcLog_NG(SVC_LOG_TP_DRV_TASK, "SvcCyttsp6DriverTask_Init err, SvcTask_Create failed with 0x%x", RetVal, 0U);
}
}
return RetVal;
}
/*******************************************************************************/