⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sam9261_touch.cpp

📁 CE5.0下矩阵式触摸板驱动
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/********************************************************************************
Now we use Matrix Key, but we may need to use timer interrupt for sampling interleave
if we want to use timer,define 'TouchNeedTimer' macro
********************************************************************************/

#include <windows.h>
#include <types.h>
#include <memory.h>
#include <ceddk.h>
#include <nkintr.h>
#include <tchddsi.h>
#include <nkintr.h>
#include <bsp.h>
#include "SAM9261_touch.h"

/********************************************************************************
* define const don`t move to .h files later
********************************************************************************/
#define		PUBLIC
#define 	PRIVATE				static

/* Reg definition */
PRIVATE volatile AT91S_AIC	*v_pAicregs = NULL;
PRIVATE volatile AT91S_PIO	*v_pPioCregs = NULL;

//same as 560T
PRIVATE volatile BYTE	*v_KEY_USE_AREA = NULL;
PRIVATE volatile BYTE	*v_KEY_RD_LT07 = NULL;
PRIVATE volatile BYTE	*v_KEY_RD_LT15 = NULL;
PRIVATE volatile BYTE	*v_KEY_RD_LT23 = NULL;
PRIVATE volatile BYTE	*v_KEY_RD_LT31 = NULL;
PRIVATE volatile BYTE	*v_KEY_WR_LT07 = NULL;
PRIVATE volatile BYTE	*v_KEY_WR_LT15 = NULL;
PRIVATE volatile BYTE	*v_KEY_WR_LT23 = NULL;

#ifdef TouchNeedTimer
PRIVATE volatile AT91S_PMC 	*v_pPMCRegs = NULL;
PRIVATE volatile AT91S_TC	*v_pTCRegs = NULL;
#endif

/********************************************************************************
* global variables definition
********************************************************************************/
DWORD gIntrTouch        = SYSINTR_NOP;
DWORD gIntrTouchChanged = SYSINTR_NOP;

extern "C" const int MIN_CAL_COUNT   = 1;

/* static variable definition */
PRIVATE INT 	TSP_CurRate = TSP_SAMPLE_RATE_HIGH;


// function implementation
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Free Memory */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PRIVATE void TSP_VirtualFree(VOID)
{
RETAILMSG(1,(TEXT("::: TSP_VirtualFree()\r\n")));
    if(v_pAicregs)
    {
        MmUnmapIoSpace((PVOID)v_pAicregs, sizeof(AT91S_AIC));
        v_pAicregs = NULL;
    }
   	if(v_pPioCregs)
    {
        MmUnmapIoSpace((PVOID)v_pPioCregs, sizeof(AT91S_PIO));
        v_pPioCregs = NULL;
    }

    if(v_KEY_USE_AREA)
    {
    	MmUnmapIoSpace((PVOID)v_KEY_USE_AREA, sizeof(BYTE));
    	v_KEY_USE_AREA = NULL;
    }
#ifdef TouchNeedTimer    
    if(v_pPMCRegs)
    {
        MmUnmapIoSpace((PVOID)v_pPMCRegs, sizeof(AT91S_PMC));
        v_pPMCRegs = NULL;
    }
   	if(v_pTCRegs)
    {
        MmUnmapIoSpace((PVOID)v_pTCRegs, sizeof(AT91S_TC));
        v_pTCRegs = NULL;
    }
#endif    
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Alloc Memory */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PRIVATE BOOL TSP_VirtualAlloc(VOID)
{
	BOOL r = FALSE;
	PHYSICAL_ADDRESS pa;	
	
RETAILMSG(1,(TEXT("::: TSP_VirtualAlloc()\r\n")));	
	do
	{
		pa.QuadPart = (UINT32)SAM9261_BASE_REG_PA_AIC;
		v_pAicregs = (volatile AT91S_AIC *)MmMapIoSpace(pa, sizeof(AT91S_AIC), FALSE);
		if (v_pAicregs == NULL)
		{
			ERRORMSG(1,(TEXT("For AICreg: VirtualAlloc failed!\r\n")));
            break;
		}
		
		pa.QuadPart = (UINT32)SAM9261_BASE_REG_PA_PIOC;
		v_pPioCregs = (volatile AT91S_PIO *)MmMapIoSpace(pa, sizeof(AT91S_PIO), FALSE);
		if (v_pPioCregs == NULL)
		{
			ERRORMSG(1,(TEXT("For PIOreg: VirtualAlloc failed!\r\n")));
            break;
		}

		pa.QuadPart = (UINT32)PERIPH_BASE;
		v_KEY_USE_AREA = (volatile BYTE *)MmMapIoSpace(pa, sizeof(BYTE) * 16, FALSE);
		if (v_KEY_USE_AREA == NULL)
		{
			ERRORMSG(1,(TEXT("For v_KEY_USE_AREA: VirtualAlloc failed!\r\n")));
            break;
		}
		else
		{
			v_KEY_RD_LT07 = v_KEY_USE_AREA + KEY_RD_LT07_OFFSET;
			v_KEY_RD_LT15 = v_KEY_USE_AREA + KEY_RD_LT15_OFFSET;
			v_KEY_RD_LT23 = v_KEY_USE_AREA + KEY_RD_LT23_OFFSET;
			v_KEY_RD_LT31 = v_KEY_USE_AREA + KEY_RD_LT31_OFFSET;
			v_KEY_WR_LT07 = v_KEY_USE_AREA + KEY_WR_LT07_OFFSET;
			v_KEY_WR_LT15 = v_KEY_USE_AREA + KEY_WR_LT15_OFFSET;
			v_KEY_WR_LT23 = v_KEY_USE_AREA + KEY_WR_LT23_OFFSET;
		}

#ifdef TouchNeedTimer		
		pa.QuadPart = (UINT32)SAM9261_BASE_REG_PA_PMC;
		v_pPMCRegs = (volatile AT91S_PMC *)MmMapIoSpace(pa, sizeof(AT91S_PMC), FALSE);
		if (v_pPMCRegs == NULL)
		{
			ERRORMSG(1,(TEXT("For PMCreg: VirtualAlloc failed!\r\n")));
            break;
		}

		pa.QuadPart = (UINT32)SAM9261_BASE_REG_PA_TC0;
		v_pTCRegs = (volatile AT91S_TC *)MmMapIoSpace(pa, sizeof(AT91S_TC), FALSE);
		if (v_pTCRegs == NULL)
		{
			ERRORMSG(1,(TEXT("For TCreg: VirtualAlloc failed!\r\n")));
            break;
		}
#endif
		r = TRUE;
	} while(0);
	
	if (r == FALSE)
	{
		TSP_VirtualFree();
RETAILMSG(1,(TEXT("::: TSP_VirtualAlloc() - Fail\r\n")));
	}
	else
	{
RETAILMSG(1,(TEXT("::: TSP_VirtualAlloc() - Success\r\n")));		
	}
	return (r);
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Iitialize TC0 */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PRIVATE VOID TSP_PowerOn(VOID)
{
#ifdef TouchNeedTimer
	UINT32	RCValue;
#endif
RETAILMSG(1,(TEXT("::: TSP_PowerOn()\r\n")));
#ifdef TouchNeedTimer	
	// Enale TC0 clock
	v_pPMCRegs->PMC_PCER = 1<<AT91C_ID_TC0;
	// Disable counter clock
	v_pTCRegs->TC_CCR = AT91C_TC_CLKDIS;
    // Select Waveform Mode mode, TIMER_DIV5_CLOCK (SCLK) ,RC Compare Trigger
	v_pTCRegs->TC_CMR = ( AT91C_TC_CLKS_TIMER_DIV5_CLOCK | AT91C_TC_WAVESEL_UP_AUTO | AT91C_TC_WAVE );
	// Set timer RC register, 1000ms sample again
	RCValue = 100 * (AT91C_TIMER0_CLOCK / 1000);
	v_pTCRegs->TC_RC = RCValue;
	// Enable RC compare Interrupt
	v_pTCRegs->TC_IER = AT91C_TC_CPCS;
// Enable and start counter clock,don't do here
//    OUTREG32(&v_pTCRegs->TC_CCR, AT91C_TC_CLKEN);		    
//    OUTREG32(&v_pTCRegs->TC_CCR, AT91C_TC_SWTRG);
#endif
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PRIVATE VOID TSP_PowerOff(VOID)
{
RETAILMSG(1,(TEXT("::: TSP_PowerOff()\r\n")));
#ifdef	TouchNeedTimer
	//Disable interrupt
	v_pTCRegs->TC_IDR = AT91C_TC_CPCS;
	v_pTCRegs->TC_CCR = AT91C_TC_CLKDIS;
#endif
}

// Disable PIOBIRQ
PRIVATE VOID DisableKeyInt(VOID)
{
	if(v_pAicregs)
	{
		v_pAicregs->AIC_IDCR = 1 << AT91C_ID_PIOB;
		v_pAicregs->AIC_ICCR = 1 << AT91C_ID_PIOB;
	}
}

// Enable PIOBIRQ 
PRIVATE VOID EnableKeyInt(VOID)
{
	if(v_pAicregs)
	{
		v_pAicregs->AIC_ICCR = 1 << AT91C_ID_PIOB;
		v_pAicregs->AIC_IECR = 1 << AT91C_ID_PIOB;
	}
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Set Timing para */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PRIVATE VOID InitializeNCS4(VOID)
{
	volatile AT91S_SMC	*v_pSmcRegs;
	volatile AT91S_PIO	*v_pPioCRegs;
	PHYSICAL_ADDRESS pa;
	
//RETAILMSG(1,(TEXT("Set NCS4 Parameter!\r\n")));	
	
	pa.QuadPart = (UINT32)SAM9261_BASE_REG_PA_SMC;
	v_pSmcRegs = (volatile AT91S_SMC *)MmMapIoSpace(pa, sizeof(AT91S_SMC), FALSE);
	
	pa.QuadPart = (UINT32)SAM9261_BASE_REG_PA_PIOC;
	v_pPioCRegs = (volatile AT91S_PIO *)MmMapIoSpace(pa, sizeof(AT91S_PIO), FALSE);

	v_pPioCRegs->PIO_ASR = TouchPanel_CS;
	v_pPioCRegs->PIO_PDR = TouchPanel_CS;

//	v_pSmcRegs->SMC_SETUP4 = (2 << 24) | (2 << 8);
//	v_pSmcRegs->SMC_PULSE4 = (0x0C << 24) | (0x0C << 16) | (0x0C << 8) | (0x0C);
//	v_pSmcRegs->SMC_CYCLE4 = (0x18 << 16) | (0x18);
	v_pSmcRegs->SMC_SETUP4 = (3 << 24) | (3 << 8);
	v_pSmcRegs->SMC_PULSE4 = (0x10 << 24) | (0x10 << 16) | (0x10 << 8) | (0x10);
	v_pSmcRegs->SMC_CYCLE4 = (0x18 << 16) | (0x18);


	v_pSmcRegs->SMC_CTRL4 = AT91C_SMC_READMODE;
	
	MmUnmapIoSpace((PVOID)v_pSmcRegs, sizeof(AT91S_SMC));
	MmUnmapIoSpace((PVOID)v_pPioCRegs, sizeof(AT91S_PIO));
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Initialize Key Interrupt */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PRIVATE VOID InitKeyInt(VOID)
{
	volatile AT91S_PIO	*pPIOCregs;
	volatile AT91S_PMC	*pPMCregs;
	volatile AT91S_AIC	*pAICregs;
	UINT32		PioBIsr;
	PHYSICAL_ADDRESS pa;
	
//RETAILMSG(1,(TEXT("Init Key Interrupt!\r\n")));		

	pa.QuadPart =  (UINT32)SAM9261_BASE_REG_PA_PMC;
	pPMCregs = (volatile AT91S_PMC *)MmMapIoSpace(pa, sizeof(AT91S_PMC), FALSE);
	
	pa.QuadPart =  (UINT32)SAM9261_BASE_REG_PA_PIOC;
	pPIOCregs = (volatile AT91S_PIO *)MmMapIoSpace(pa, sizeof(AT91S_PIO), FALSE);
	
	pa.QuadPart =  (UINT32)SAM9261_BASE_REG_PA_AIC;
	pAICregs = (volatile AT91S_AIC *)MmMapIoSpace(pa, sizeof(AT91S_AIC), FALSE);
	
	// Config PB31 as Touch Interrupt
	pPMCregs->PMC_PCER = (1 << AT91C_ID_PIOC);
	pPIOCregs->PIO_IFER = TouchPanel_IRQ;
	pPIOCregs->PIO_ODR = TouchPanel_IRQ;
	PioBIsr = pPIOCregs->PIO_ISR;
	pPIOCregs->PIO_IER = TouchPanel_IRQ;
	pPIOCregs->PIO_PER = TouchPanel_IRQ;
	pAICregs->AIC_SVR[AT91C_ID_PIOB] = (UINT32)AT91C_ID_PIOB;
	pAICregs->AIC_SMR[AT91C_ID_PIOB] = (INTR_TOUCH_PRIORITY | AT91C_AIC_SRCTYPE_INT_LEVEL_SENSITIVE);
	
	MmUnmapIoSpace((PVOID)pPMCregs, sizeof(AT91S_PMC));
	MmUnmapIoSpace((PVOID)pPIOCregs, sizeof(AT91S_PIO));
	MmUnmapIoSpace((PVOID)pAICregs, sizeof(AT91S_AIC));
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Load dll , not great 1 */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
LONG DdsiTouchPanelAttach(VOID)
{
RETAILMSG(1,(TEXT("::: DdsiTouchPanelAttach(), Load Dll\r\n")));
	InitializeNCS4();
	InitKeyInt();
	
    return(0);
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* unload dll */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
LONG DdsiTouchPanelDetach(VOID)
{
RETAILMSG(1,(TEXT("::: DdsiTouchPanelDetach(), UnLoad Dll\r\n")));
    return(0);
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Touch disable */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PUBLIC VOID DdsiTouchPanelDisable(VOID)
{
//RETAILMSG(1, (TEXT("::: DdsiTouchPanelDisable()\r\n")));  
    //DisableKeyInt();
    if( v_pAicregs )
    {	// Disable Touch interrupt, Maybe needn't call,because TouchPanelDisable can do disable Key Interrupt
    	TSP_PowerOff();
    	TSP_VirtualFree();
    	KernelIoControl(IOCTL_HAL_RELEASE_SYSINTR, &gIntrTouch, sizeof(UINT32), NULL, 0, NULL);
    	gIntrTouch = SYSINTR_NOP;
#ifdef	TouchNeedTimer	
    	KernelIoControl(IOCTL_HAL_RELEASE_SYSINTR, &gIntrTouchChanged, sizeof(UINT32), NULL, 0, NULL);
    	gIntrTouchChanged = SYSINTR_NOP;
#endif
    }
}

/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
/* Touch panel initialize */
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
PUBLIC BOOL DdsiTouchPanelEnable(VOID)
{
	BOOL r;
	UINT32 Irq;
	
RETAILMSG(1, (TEXT("::: DdsiTouchPanelEnable()\r\n")));	
	r = TSP_VirtualAlloc();
	
	Irq = IRQ_PIOIRQ;
	/* Note! OEMIoControl must implement IOCTL_HAL_REQUEST_SYSINTR */
	if (!KernelIoControl(IOCTL_HAL_REQUEST_SYSINTR, &Irq, sizeof(UINT32), &gIntrTouch, sizeof(UINT32), NULL))
	{
		RETAILMSG(1, (TEXT("ERROR: Failed to request the touch sysintr.\r\n")));
        gIntrTouch = SYSINTR_UNDEFINED;
        return(FALSE);
	}	
#ifdef	TouchNeedTimer	
	Irq = IRQ_TIMER0;
	if (!KernelIoControl(IOCTL_HAL_REQUEST_SYSINTR, &Irq, sizeof(UINT32), &gIntrTouchChanged, sizeof(UINT32), NULL))
    {
        RETAILMSG(1, (TEXT("ERROR: Failed to request the touch changed sysintr.\r\n")));
        gIntrTouchChanged = SYSINTR_UNDEFINED;
        return(FALSE);
    }  
#endif
    if (r)
    {
        TSP_PowerOn();
    }
    
    return (r);
}

PRIVATE BOOL TSP_CalibrationPointGet(TPDC_CALIBRATION_POINT *pTCP)
{

    INT32	cDisplayWidth  = pTCP->cDisplayWidth;
    INT32 	cDisplayHeight = pTCP->cDisplayHeight;

    switch (pTCP -> PointNumber)
    {
    case    0:
        pTCP->CalibrationX = cDisplayWidth  / 2;
        pTCP->CalibrationY = cDisplayHeight / 2;
        break;

    case    1:
        pTCP->CalibrationX = cDisplayWidth  / 5;
        pTCP->CalibrationY = cDisplayHeight / 5;
        break;

    case    2:
        pTCP->CalibrationX = cDisplayWidth  / 5;
        pTCP->CalibrationY = cDisplayHeight / 5 * 4;
        break;

    case    3:
        pTCP->CalibrationX = cDisplayWidth  / 5 * 4;
        pTCP->CalibrationY = cDisplayHeight / 5 * 4;
        break;

    case    4:
        pTCP->CalibrationX = cDisplayWidth  / 5 * 4;
        pTCP->CalibrationY = cDisplayHeight / 5;
        break;

    default:
        pTCP->CalibrationX = cDisplayWidth  / 2;
        pTCP->CalibrationY = cDisplayHeight / 2;

        SetLastError(ERROR_INVALID_PARAMETER);
        return (FALSE);
    }

    RETAILMSG(0, (TEXT("::: TSP_CalibrationPointGet()\r\n")));
    RETAILMSG(0, (TEXT("cDisplayWidth        : %4X\r\n"), cDisplayWidth     ));
    RETAILMSG(0, (TEXT("cDisplayHeight       : %4X\r\n"), cDisplayHeight    ));
    RETAILMSG(0, (TEXT("pTCP -> PointNumber  : %4d\r\n"), pTCP->PointNumber));

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -