keymatrix.cpp
来自「SAMSUNG S3C6410 CPU BSP for winmobile6」· C++ 代码 · 共 1,287 行 · 第 1/3 页
CPP
1,287 行
DWORD KBDISRThread(KeyMatrix *pp2k)
{
RETAILMSG(INIT_MSG,(TEXT("[KEYBD]KBDISRThread:\r\n")));
pp2k->IsrThreadProc();
return 0;
}
/****************************************************************************/
/*****************************************************************************
* Function Name : IsrThreadStart
* Function Desc : IST start function
*
*/
BOOL KeyMatrix::IsrThreadStart()
{
HANDLE hthrd;
RETAILMSG(INIT_MSG,(TEXT("+[KEYBD]IsrThreadStart:\r\n")));
hthrd = CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)KBDISRThread,this,0,NULL);
// Since we don't need the handle, close it now.
CloseHandle(hthrd);
#if defined(project_wpc)
v_hevtKeyPressed = CreateEvent(NULL, FALSE, FALSE, TEXT("_KeyPress"));
#endif
RETAILMSG(INIT_MSG,(TEXT("-[KEYBD]IsrThreadStart:\r\n")));
return TRUE;
}
/****************************************************************************/
/*****************************************************************************
* Function Name : KeybdPowerOn
* Function Desc : Power on function
* Key array (mask, cnt) initialization, GPIO, Interrupt Initialization
*
*/
BOOL KeyMatrix::KeybdPowerOn()
{
RETAILMSG(INIT_MSG,(TEXT("++[KEYBD]KeyMatrix::KeybdPowerOn\r\n")));
//
// enable the Keypad Clock (PCLK)
//
Keypad_Clock_On(TRUE);
pKeyPadReg->KEYIFCON = INT_F_DISABLE|INT_R_ENABLE|DF_EN_EN|FC_EN_EN;
//Keypad interfae debouncing filter clock division register
pKeyPadReg->KEYIFFC = FC_DIV_VAL(FT_CLK_DIV);
#if (CPU_NAME == S3C6410)
#if ((MATRIX_LAYOUT == LAYOUT0)||(MATRIX_LAYOUT == LAYOUT2))
pKeyPadReg->KEYIFCOL = (0x00<<8);
#elif (MATRIX_LAYOUT == LAYOUT1)
pKeyPadReg->KEYIFCOL = (0x7<<8);
#endif
#elif (CPU_NAME == S3C6400)
#if (MATRIX_LAYOUT == LAYOUT0)
pKeyPadReg->KEYIFCOL = (0x00<<8);
#else
pKeyPadReg->KEYIFCOL = (0x3f<<8);
#endif
#endif
VarInit();
KScan_SetINTMode();
RETAILMSG(INIT_MSG,(TEXT("--[KEYBD]KeyMatrix::KeybdPowerOn\r\n")));
return(TRUE);
}
/****************************************************************************/
/*****************************************************************************
* Function Name : KeybdPowerOff
* Function Desc : Power off function
* Mask KEYIF INT, Column Low
*
*/
BOOL KeyMatrix::KeybdPowerOff()
{
DEBUGMSG(1,(TEXT("++KeyMatrix::KeybdPowerOff\r\n")));
// Clear Pressed/Released Interrupt
KEYIF_Status_Clear();
// select all column - Set Keypad column GPIO to output(low)
GPIO_CtrlHandler(ENUM_COL, ENUM_AUXFUNC);
KEYIF_Column_Set(0x0);
// configure - Set Keypad row GPIO to [Key PAD ROW]
GPIO_CtrlHandler(ENUM_ROW, ENUM_AUXFUNC);
//Clock Off
Keypad_Clock_On(FALSE);
DEBUGMSG(1,(TEXT("--KeyMatrix::KeybdPowerOff\r\n")));
return(TRUE);
}
/****************************************************************************/
/*****************************************************************************
* Function Name : GPIO Handling function
* Function Desc : GPIO_PuEnable, GPIO_CtrlHandler
* Pull up Enable/Disable
* GPIO Control register configuration only related to KEYPAD
* GPIO Data register setting only related to KEYPAD
*
*/
/**
[iClass] 0: Column, 1: Row
[bFlag] 0: Pull up Enable, 1 : Pull up Disable
*/
static void GPIO_PuEnable(ENUM_COL_ROW iClass, bool bFlag)
{
if(iClass == ENUM_COL) // Column setting
{
if(bFlag) // Pull up Enable
{
pGPIOReg->GPLPUD = pGPIOReg->GPLPUD | (0xaaaa<<0); // KBC_0~7
}
else // Pull up Disable
{
pGPIOReg->GPLPUD = pGPIOReg->GPLPUD & ~ (0xffff<<0); // KBC_0~7
}
}
else // Row Setting
{
if(bFlag) // Pull up Enable
{
pGPIOReg->GPKPUD = pGPIOReg->GPKPUD | (0xaaaa<<16); // KBR_0~7
}
else // Pull up Disable
{
pGPIOReg->GPKPUD = pGPIOReg->GPKPUD & ~ (0xffff<<16); // KBR_0~7
}
}
}
/**
[iClass] 0: Column, 1: Row
[iLevel] 0: INPUT, 1 : OUTPUT, 2 : Aux. Function, 3 : Reserved
*/
static void GPIO_CtrlHandler(ENUM_COL_ROW iClass, ENUM_GPIO_FUNC iLevel)
{
#if (CPU_NAME == S3C6410)
#if ((MATRIX_LAYOUT == LAYOUT0)||(MATRIX_LAYOUT == LAYOUT2))
if(iClass == ENUM_COL) // Column setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x0<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
case ENUM_OUTPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x11111111<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
case ENUM_AUXFUNC :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x33333333<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
default : //ENUM_RESERVED
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x44444444<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
}
}
else if(iClass == ENUM_ROW) // Row Setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x0<<0); //row break;
break;
case ENUM_OUTPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x11111111<<0); //row break;
break;
case ENUM_AUXFUNC :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x33333333<<0); //KBR_0(GPK8)~ KBR_7(GPK15)
break;
default : //ENUM_RESERVED
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x44444444<<0); //KBR_0(GPK8)~ KBR_7(GPK15)
break;
}
}
else
{
DEBUGMSG(1,(TEXT("Invalid Parameter\r\n")));
}
#elif (MATRIX_LAYOUT == LAYOUT1)
if(iClass == ENUM_COL) // Column setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xfffff<<12)) | (0x00000<<12); //KBC_3(GPL3)~ KBC_7(GPL7)
break;
case ENUM_OUTPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xfffff<<12)) | (0x11111<<12); //KBC_3(GPL3)~ KBC_7(GPL7)
break;
case ENUM_AUXFUNC :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xfffff<<12)) | (0x33333<<12); //KBC_3(GPL3)~ KBC_7(GPL7)
break;
default : //ENUM_RESERVED
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xfffff<<12)) | (0x44444<<12); //KBC_3(GPL3)~ KBC_7(GPL7)
break;
}
}
else if(iClass == ENUM_ROW) // Row Setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xff<<0)) | (0x00<<0); //KBR_0(GPK8)~ KBR_1(GPK9)
break;
case ENUM_OUTPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xff<<0)) | (0x11<<0); //KBR_0(GPK8)~ KBR_1(GPK9)
break;
case ENUM_AUXFUNC :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xff<<0)) | (0x33<<0); //KBR_0(GPK8)~ KBR_1(GPK9)
break;
default : //ENUM_RESERVED
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xff<<0)) | (0x44<<0); //KBR_0(GPK8)~ KBR_1(GPK9)
break;
}
}
else
{
DEBUGMSG(1,(TEXT("Invalid Parameter\r\n")));
}
#endif
#elif (CPU_NAME == S3C6400)
#if (MATRIX_LAYOUT == LAYOUT0)
if(iClass == ENUM_COL) // Column setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x0<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
case ENUM_OUTPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x11111111<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
case ENUM_AUXFUNC :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x33333333<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
default : //ENUM_RESERVED
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xffffffff<<0)) | (0x44444444<<0); //KBC_0(GPL0)~ KBC_8(GPL7)
break;
}
}
else if(iClass == ENUM_ROW) // Row Setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x0<<0); //row break;
break;
case ENUM_OUTPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x11111111<<0); //row break;
break;
case ENUM_AUXFUNC :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x33333333<<0); //KBR_0(GPK8)~ KBR_7(GPK15)
break;
default : //ENUM_RESERVED
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x44444444<<0); //KBR_0(GPK8)~ KBR_7(GPK15)
break;
}
}
else
{
DEBUGMSG(1,(TEXT("Invalid Parameter\r\n")));
}
#else
if(iClass == ENUM_COL) // Column setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xff<<24)) | (0x0<<24); //KBC_6(GPL6)~ KBC_7(GPL7)
break;
case ENUM_OUTPUT :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xff<<24)) | (0x11<<24); //KBC_6(GPL6)~ KBC_7(GPL7)
break;
case ENUM_AUXFUNC :
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xff<<24)) | (0x33<<24); //KBC_6(GPL6)~ KBC_7(GPL7)
break;
default : //ENUM_RESERVED
pGPIOReg->GPLCON0=
(pGPIOReg->GPLCON0 & ~(0xff<<24)) | (0x44<<24); //KBC_6(GPL6)~ KBC_7(GPL7)
break;
}
}
else if(iClass == ENUM_ROW) // Row Setting
{
switch(iLevel)
{
case ENUM_INPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x0<<0); //row break;
break;
case ENUM_OUTPUT :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x11111111<<0); //row break;
break;
case ENUM_AUXFUNC :
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x33333333<<0); //KBR_0(GPK8)~ KBR_7(GPK15)
break;
default : //ENUM_RESERVED
pGPIOReg->GPKCON1=
(pGPIOReg->GPKCON1 & ~(0xffffffff<<0)) | (0x44444444<<0); //KBR_0(GPK8)~ KBR_7(GPK15)
break;
}
}
else
{
DEBUGMSG(1,(TEXT("Invalid Parameter\r\n")));
}
#endif
#endif
}
/**
[dVal] Value of KBC
*/
static void KEYIF_Column_Set(DWORD dVal)
{
pKeyPadReg->KEYIFCOL = (dVal & 0xff);
}
static void KEYIF_Column_Bitset(bool bVal, int cIdx)
{
#if (CPU_NAME == S3C6410)
#if ((MATRIX_LAYOUT == LAYOUT0)||(MATRIX_LAYOUT == LAYOUT2))
if(bVal)
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0x1 << cIdx);
}
else
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0xff & ~(0x1 << cIdx));
}
#elif (MATRIX_LAYOUT == LAYOUT1)
if(bVal)
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0x1 << (cIdx+3));
}
else
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0xff & ~(0x1 << (cIdx+3)));
}
#endif
#elif (CPU_NAME == S3C6400)
#if (MATRIX_LAYOUT == LAYOUT0)
if(bVal)
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0x1 << cIdx);
}
else
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0xff & ~(0x1 << cIdx));
}
#else
if(bVal)
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0x1 << (cIdx+6));
}
else
{
pKeyPadReg->KEYIFCOL = pKeyPadReg->KEYIFCOL | (0xff & ~(0x1 << (cIdx+6)));
}
#endif
#endif
}
static DWORD KEYIF_Row_Read(void)
{
return pKeyPadReg->KEYIFROW;
}
static void KEYIF_Status_Clear(void)
{
pKeyPadReg->KEYIFSTSCLR = CLEAR_P_INT|CLEAR_R_INT; // Clear Pressed/Released Interrupt
}
void Keypad_Clock_On(BOOL bOn)
{
if (bOn)
{
pSysConReg->PCLK_GATE |= KEY_POWER_ON;
}
else
{
pSysConReg->PCLK_GATE &= ~KEY_POWER_ON;
}
return;
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?