s3c2410触摸屏驱动

整理文档很辛苦,赏杯茶钱您下走!

免费阅读已结束,点击下载阅读编辑剩下 ...

阅读已结束,您可以下载文档离线阅读编辑

资源描述

s3c2410触摸屏驱动(2.6内核)分析s3c2410触摸屏驱动(2.6内核)分析驱动不是很多,在此把它贴出来然后加上必要的注释:#includelinux/config.h#includelinux/errno.h#includelinux/kernel.h#includelinux/module.h#includelinux/slab.h#includelinux/input.h#includelinux/init.h#includelinux/serio.h#includelinux/delay.h#includeasm/io.h#includeasm/irq.h#includeasm/arch/regs-adc.h#includeasm/arch/regs-gpio.h#includeasm/arch/s3c2410-ts.h#includeasm/hardware/clock.h/*Forts.dev.id.version*/#defineS3C2410TSVERSION0x0101#defineWAIT4INT(x)(((x)8)|S3C2410_ADCTSC_YM_SEN|S3C2410_ADCTSC_YP_SEN|S3C2410_ADCTSC_XP_SEN|S3C2410_ADCTSC_XY_PST(3))#defineAUTOPST(S3C2410_ADCTSC_YM_SEN|S3C2410_ADCTSC_YP_SEN|S3C2410_ADCTSC_XP_SEN|S3C2410_ADCTSC_AUTO_PST|S3C2410_ADCTSC_XY_PST(0))#defineDEBUG_LVLKERN_DEBUGMODULE_AUTHOR(ArnaudPatardarnaud.patard@rtp-net.org);MODULE_DESCRIPTION(s3c2410touchscreendriver);MODULE_LICENSE(GPL);/**Definitions&globalarrays.*/staticchar*s3c2410ts_name=s3c2410TouchScreen;/**Per-touchscreendata.*/structs3c2410ts{structinput_devdev;longxp;longyp;intcount;intshift;charphys[32];};staticstructs3c2410tsts;staticvoid__iomem*base_addr;staticinlinevoids3c2410_ts_connect(void){s3c2410_gpio_cfgpin(S3C2410_GPG12,S3C2410_GPG12_XMON);s3c2410_gpio_cfgpin(S3C2410_GPG13,S3C2410_GPG13_nXPON);s3c2410_gpio_cfgpin(S3C2410_GPG14,S3C2410_GPG14_YMON);s3c2410_gpio_cfgpin(S3C2410_GPG15,S3C2410_GPG15_nYPON);}staticvoidtouch_timer_fire(unsignedlongdata){unsignedlongdata0;unsignedlongdata1;intupdown;/*读取stylus的状态0=Stylusdownstate1=Stylusupstate*/data0=readl(base_addr+S3C2410_ADCDAT0);data1=readl(base_addr+S3C2410_ADCDAT1);updown=(!(data0&S3C2410_ADCDAT0_UPDOWN))&&(!(data1&S3C2410_ADCDAT1_UPDOWN));/*更新stylus状态寄存器updown:1=down0=up*//*touch_timer_fire这个函数主要实现以下功能:1、stylusdown的时候,在中断函数stylus_updown里面被调用,此时缓存区没有数据,ts.count为0,所以只是简单的设置ad转换的模式,然后开启ad转换。2、但ADC中断函数stylus_action把缓冲区填满的时候,作为中断后半段函数稍后被调用,此时ts.count为4,算出其平均值后,交给事件处理层(EventHandler)处理,主要是填写缓冲,然后唤醒等待输入数据的进程。3、stylus抬起,等到缓冲区填满后(可能会包含一些无用的数据)被调用,这时候判断出stylusup,报告stylusup事件,重新等待stylusdown。if(updown){if(ts.count!=0){功能2/*求平均值*/ts.xp=ts.shift;ts.yp=ts.shift;#ifdefCONFIG_TOUCHSCREEN_S3C2410_DEBUG{structtimevaltv;do_gettimeofday(&tv);printk(DEBUG_LVLT:%06d,X:%03ld,Y:%03ld\n,(int)tv.tv_usec,ts.xp,ts.yp);}#endif/*报告x、y的绝对坐标值*/input_report_abs(&ts.dev,ABS_X,ts.xp);input_report_abs(&ts.dev,ABS_Y,ts.yp);/*报告按键事件,键值为1(代表触摸屏对应的按键被按下)*/input_report_key(&ts.dev,BTN_TOUCH,1);/*报告触摸屏的状态,1表明触摸屏被按下*/input_report_abs(&ts.dev,ABS_PRESSURE,1);/*等待接收方受到数据后回复确认,用于同步*/input_sync(&ts.dev);}功能1ts.xp=0;ts.yp=0;ts.count=0;writel(S3C2410_ADCTSC_XP_PULL_UP_DIS|AUTOPST,base_addr+S3C2410_ADCTSC);/*设置触摸屏的模式为AUTOPST*/writel(readl(base_addr+S3C2410_ADCCON)|S3C2410_ADCCON_ENABLE_START,base_addr+S3C2410_ADCCON);/*启动ADC转换*/}else{功能3ts.count=0;/*报告按键事件,键值为1(代表触摸屏对应的按键被释放)*/input_report_key(&ts.dev,BTN_TOUCH,0);/*报告触摸屏的状态,0表明触摸屏没被按下*/input_report_abs(&ts.dev,ABS_PRESSURE,0);/*等待接收方受到数据后回复确认,用于同步*/input_sync(&ts.dev);/*进入s3c2410触摸屏提供的,WaitingforInterruptMode,waitsforStylusdown*/writel(WAIT4INT(0),base_addr+S3C2410_ADCTSC);}}staticstructtimer_listtouch_timer=TIMER_INITIALIZER(touch_timer_fire,0,0);staticirqreturn_tstylus_updown(intirq,void*dev_id,structpt_regs*regs){unsignedlongdata0;unsignedlongdata1;intupdown;/*读取ADCDAT0/1寄存器,判断Stylus的状态:0=Stylusdownstate1=Stylusupstate*/data0=readl(base_addr+S3C2410_ADCDAT0);data1=readl(base_addr+S3C2410_ADCDAT1);updown=(!(data0&S3C2410_ADCDAT0_UPDOWN))&&(!(data1&S3C2410_ADCDAT1_UPDOWN));/*更新stylus状态寄存器updown:1=down0=up*//*TODOweshouldnevergetaninterruptwithupdownsetwhile*thetimerisrunning,butmaybeweoughttoverifythatthe*timerisn'trunninganyways.*//*判断出stylusdown,调用touch_timer_fire函数*/if(updown)touch_timer_fire(0);returnIRQ_HANDLED;}staticirqreturn_tstylus_action(intirq,void*dev_id,structpt_regs*regs){unsignedlongdata0;unsignedlongdata1;data0=readl(base_addr+S3C2410_ADCDAT0);data1=readl(base_addr+S3C2410_ADCDAT1);/*触摸屏的XY线接的是反的,所以只好这样做了另外,可以参考这个方法:=637&goto=lastpost*//**************************modifybylfc********************/ts.yp+=data0&S3C2410_ADCDAT0_XPDATA_MASK;ts.xp+=data1&S3C2410_ADCDAT1_YPDATA_MASK;/***********************************************************/ts.count++;if(ts.count(1ts.shift)){/*缓冲区未满,再次激活ADC转换*/writel(S3C2410_ADCTSC_XP_PULL_UP_DIS|AUTOPST,base_addr+S3C2410_ADCTSC);writel(readl(base_addr+S3C2410_ADCCON)|S3C2410_ADCCON_ENABLE_START,base_addr+S3C2410_ADCCON);}else{/*缓冲区满,激活下半部处理程序touch_timer_fire,处理接收数据*/mod_timer(&touch_timer,jiffies+1);writel(WAIT4INT(1),base_addr+S3C2410_ADCTSC);}returnIRQ_HANDLED;}staticstructclk*adc_clock;/**Thefunctionsforinserting/removingusasamodule.*/staticint__inits3c2410ts_probe(structdevice*dev){structs3c2410_ts_mach_info*info;info=(structs3c2410_ts_mach_info*)dev-platform_data;注:s3c2410_ts_mach_info这个结构需要我们去填充,里面存放的是触摸屏需要的一些配置参数,见下面的附录部分。if(!info){printk(KERN_ERRHm...toobad:noplatformdataforts\n);return-EINVAL;}#ifdefCONFIG_TOUCHSCREEN_S3C2410_DEBUGprintk(DEBUG_LVLEnterings3c2410ts_init\n);#endifadc_clock=clk_get(NULL,adc

1 / 10
下载文档,编辑使用

©2015-2020 m.777doc.com 三七文档.

备案号:鲁ICP备2024069028号-1 客服联系 QQ:2149211541

×
保存成功