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 + -
显示快捷键?