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

📄 mc68328digi.c

📁 老外写的触摸屏驱动程序
💻 C
📖 第 1 页 / 共 4 页
字号:
/*----------------------------------------------------------------------------*//* mc68328digi.c,v 1.2 2001/02/12 11:14:10 pney Exp * * linux/drivers/char/mc68328digi.c - Touch screen driver. * * Author: Philippe Ney <philippe.ney@smartdata.ch> * Copyright (C) 2001 SMARTDATA <www.smartdata.ch> * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * Thanks to: *    Kenneth Albanowski for is first work on a touch screen driver. *    Alessandro Rubini for is "Linux device drivers" book. *    Ori Pomerantz for is "Linux Kernel Module Programming" guide. * * Updates: *   2001-03-07 Pascal bauermeister <pascal.bauermeister@smartdata.ch> *              - Adapted to work ok on xcopilot; yet untested on real Palm. *              - Added check for version in ioctl() * *   2001-03-21 Pascal bauermeister <pascal.bauermeister@smartdata.ch> *              - bypass real hw uninits for xcopilot. Now xcopilot is *                happy. It even no longer generates pen irq while this *                irq is disabled (I'd like to understand why, so that *                I can do the same in mc68328digi_init() !). * *   2001-10-23 Daniel Potts <danielp@cse.unsw.edu.au> *              - support for uCdimm/68VZ328. I use SPI 2 which maps to the *                same addresses as for 68EZ328 and requries less changes to *                the code. For CS I use PF_A22; CSD0/CAS0 is not made  *                available off the uCdimm. *                PF1 (/IRQ5) is already used on uCdimm by the ethernet *                controller. We use /IRQ6 instead (PD7). *              - kill_fasync and request_irq fixes for 2.4.x (only) support. * * * Hardware:      Motorola MC68EZ328 DragonBall-EZ *                Burr-Brown ADS7843 Touch Screen Controller *                Rikei REW-A1 Touch Screen * * OS:            uClinux version 2.0.38.1pre3 * * Connectivity:  Burr-Brown        DragonBall *                PENIRQ     ---->  PD7  &  PD4 (with a 100k resistor) *          //      BUSY       ---->  PF5  //changed by duwei 06/02/2003 *           //     CS         ---->  PB4   //changed by duwei 06/02/2003 *                DIN        ---->  PE0 *                DOUT       ---->  PE1 *                DCLK       ---->  PE2 * There are some changed in the current platform: by duwei 03/20/2003 *     ADS7843: /PENIRQ ----+----[100k resistor]---- : VCC *                          | *					+----------------------- VZ328: /IRQ6(PD7) * States graph: * *         ELAPSED & PEN_UP *         (re-init)             +------+ *     +------------------------>| IDLE |<------+ *     |                         +------+       | *     |                           |            | ELAPSED *     |  +------------------------+            | (re-init) *     |  |       PEN_IRQ                       | *     |  |       (disable pen_irq)             |  *     |  |       (enable & set timer)          |  *     |  |                                     | *     | \/                                     | *   +------+                                   | *   | WAIT |                                   | *   +------+                                   | *   /\   |                                     |  *   |    |             +---------------+-------+------+---------------+ *   |    |             |               |              |               | *   |    |             |               |              |               | *   |    |        +--------+      +-------+      +--------+      +--------+ *   |    +------->| ASK X  |      | ASK Y |      | READ X |      | READ Y | *   |  ELAPSED &  +--------+      +-------+      +--------+      +--------+ *   |  PEN_DOWN       |           /\    |         /\    |         /\    | *   |  (init SPIM)    +-----------'     +---------'     +---------'     | *   |  (set timer)    XCH_COMPLETE      XCH_COMPLETE    XCH_COMPLETE    | *   |                                                                   | *   |                                                                   | *   |                                                                   | *   +-------------------------------------------------------------------+ *                               XCH_COMPLETE *                               (release SPIM) *                               (set timer) * * * Remarks: I added some stuff for port on 2.2 and 2.4 kernels but currently *          this version works only on 2.0 because not tested on 2.4 yet. *          Someone interested? * *//*----------------------------------------------------------------------------*/#include <linux/kernel.h>     /* We're doing kernel work */#include <linux/module.h>     /* Specifically, a module */#include <linux/interrupt.h>  /* We want interrupts */#include <linux/miscdevice.h> /* for misc_register() and misc_deregister() */#include <linux/fs.h>         /* for struct 'file_operations' */#include <linux/timer.h>     /* for timeout interrupts */#include <linux/param.h>     /* for HZ. HZ = 100 and the timer step is 1/100 */#include <linux/sched.h>     /* for jiffies definition. jiffies is incremented                              * once for each clock tick; thus it's incremented			      * HZ times per secondes.*/#include <linux/mm.h>        /* for verify_area *///#include <linux/malloc.h>    /* for kmalloc *///changed by duwei 03/19/2003#include <linux/slab.h>    /* for kmalloc */#include <linux/init.h>#include <asm/irq.h>         /* For IRQ_MACHSPEC *//*----------------------------------------------------------------------------*//*----------------------------define------------------------------------------*/#define CONFIG_M68VZ328 1#define CONFIG_UCDIMM   1  //added by duwei 03/21/2003/*----------------------------------------------------------------------------*/#if defined(CONFIG_M68328)/* These are missing in MC68328.h. I took them from MC68EZ328.h temporarily, * but did not dare modifying MC68328.h yet (don't want to break things and * have no time now to do regression testings) *   - Pascal Bauermeister */#define ICR_ADDR        0xfffff302#define ICR_POL5        0x0080  /* Polarity Control for IRQ5 */#define IMR_MIRQ5       (1 << IRQ5_IRQ_NUM)     /* Mask IRQ5 */#define IRQ5_IRQ_NUM    20      /* IRQ5 */#define PBPUEN          BYTE_REF(PBPUEN_ADDR)#define PBPUEN_ADDR     0xfffff40a              /* Port B Pull-Up enable reg */#define PB_CSD0_CAS0    0x10    /* Use CSD0/CAS0 as PB[4] */#define PDSEL           BYTE_REF(PDSEL_ADDR)#define PDSEL_ADDR      0xfffff41b              /* Port D Select Register */#define PD_IRQ1         0x10    /* Use IRQ1 as PD[4] */#define PF_A22          0x20    /* Use A22       as PF[5] */#define PF_IRQ5         0x02    /* Use IRQ5      as PF[1] */#define SPIMCONT        WORD_REF(SPIMCONT_ADDR)#define SPIMCONT_ADDR   0xfffff802#define SPIMCONT_SPIMEN         SPIMCONT_RSPIMEN#elif defined(CONFIG_M68EZ328)# include <asm/MC68EZ328.h>  /* bus, port and irq definition of DragonBall EZ */#elif defined(CONFIG_M68VZ328)# include <asm/MC68VZ328.h>#else# error "mc68328digi: a known machine not defined."#endif//#include <linux/mc68328digi.h>#include "mc68328digi.h"  //added by duwei 03/19/2003/*----------------------------------------------------------------------------*//* Debug */#if 0#if 0# define DPRINTK printk("%0: [%03d,%03d] ", __file__, \                        current_pos.x, current_pos.y); \                        printk#else# define DPRINTK __dummy__  static void __dummy__(const char* fmt, ...) {}#endif#endif/*----------------------------------------------------------------------------*/static const char* __file__ = __FILE__;/*----------------------------------------------------------------------------*//* * Kernel compatibility. * Kernel > 2.2.3, include/linux/version.h contain a macro for KERNEL_VERSION */#include <linux/version.h>#ifndef KERNEL_VERSION#define KERNEL_VERSION(a,b,c)  (((a) << 16) + ((b) << 8) + (c))#endif/* * Conditional compilation. LINUX_VERSION_CODE is the code of this version * (as per KERNEL_VERSION) */#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,2,0))#include <asm/uaccess.h>    /* for put_user     */#include <linux/poll.h>     /* for polling fnct */#endif/* * time limit  * Used for a whole conversion (x & y) and to clock the Burr-Brown to fall the * BUSY signal down (otherwise, pen cannot generate irq anymore). * If this limit run out, an error is generated. In the first case, the driver * could recover his normal state. In the second, the BUSY signal cannot be * fallen down and the device have to be reseted. * This limit is defined as approximatively the double of the deglitch one. */#define CONV_TIME_LIMIT    50      /* ms *//*  * Length of the data structure */#define DATA_LENGTH       sizeof(struct ts_pen_info)/* * Size of the buffer for the event queue */#define TS_BUF_SIZE        32*DATA_LENGTH/* * Minor number for the touch screen device. Major is 10 because of the misc  * type of the driver. */#define MC68328DIGI_MINOR    9/* * SPIMCONT fields for this app (not defined in asm/MC68EZ328.h). */#define SPIMCONT_DATARATE ( 7 <<SPIMCONT_DATA_RATE_SHIFT)/* SPICLK = CLK / 512 */#define SPIMCONT_BITCOUNT (15<< 0)                      /* 16 bits transfert  *//* * SPIMCONT used values. */#define SPIMCONT_INIT (SPIMCONT_DATARATE    | \                       SPIMCONT_ENABLE      | \                       SPIMCONT_XCH      *0 | \                       SPIMCONT_IRQ      *0 | \                       SPIMCONT_IRQEN       | \                       SPIMCONT_PHA         | \                       SPIMCONT_POL         | \                       SPIMCONT_BITCOUNT      )/* * ADS7843 fields (BURR-BROWN Touch Screen Controller). */#define ADS7843_START_BIT (1<<7)#define ADS7843_A2        (1<<6)#define ADS7843_A1        (1<<5)#define ADS7843_A0        (1<<4)#define ADS7843_MODE      (1<<3)  /* HIGH = 8, LOW = 12 bits conversion */#define ADS7843_SER_DFR   (1<<2)  /* LOW = differential mode            */#define ADS7843_PD1       (1<<1)  /* PD1,PD0 = 11  PENIRQ disable       */#define ADS7843_PD0       (1<<0)  /* PD1,PD0 = 00  PENIRQ enable        *//* * SPIMDATA used values. *//* * Ask for X conversion. Disable PENIRQ. */#define SPIMDATA_ASKX   (ADS7843_START_BIT   | \                         ADS7843_A2          | \			 ADS7843_A1        *0| \			 ADS7843_A0          | \                         ADS7843_MODE      *0| \                         ADS7843_SER_DFR   *0| \                         ADS7843_PD1         | \                         ADS7843_PD0            )/* * Ask for Y conversion. Disable PENIRQ. */#define SPIMDATA_ASKY   (ADS7843_START_BIT   | \                         ADS7843_A2        *0| \ 			 ADS7843_A1        *0| \	 	 	 ADS7843_A0          | \                         ADS7843_MODE      *0| \                         ADS7843_SER_DFR   *0| \                         ADS7843_PD1         | \                         ADS7843_PD0            )/* * Enable PENIRQ. */#define SPIMDATA_NOP    (ADS7843_START_BIT   | \                         ADS7843_A2        *0| \ 			 ADS7843_A1        *0| \	 	 	 ADS7843_A0        *0| \                         ADS7843_MODE      *0| \                         ADS7843_SER_DFR   *0| \                         ADS7843_PD1       *0| \                         ADS7843_PD0       *0   )/* * Generate clock to fall pull BUSY signal. * No start bit to avoid generating a BUSY at end of the transfert. */#define SPIMDATA_NULL    0/* * Useful masks. */#if defined (CONFIG_UCDIMM)#define PEN_MASK	PD_IRQ6  /* pen irq signal from the Burr-Brown is */#define PEN_MASK_2	PD_IRQ1  /* connected to 2 pins of the DragonBall */                             /* (bit 2 port F and bit 4 port D)       *///#define BUSY_MASK	PF_A22//#define CS_MASK		PF_CSA1#define BUSY_MASK   PB_TIN_TOUT /* use PB6 as the BUSY signal channel */#define CS_MASK     PG_EMUIRQ    /* use PG2 as the CS signal channel.added bu duwei 03/21/2003 *///#define CS_MASK     PF_CLKO    /* use PF2 as the CS signal channel.added by liusen 07/08/2004 *///#define CS_MASK     PG_EMUCS     /*use PG4 as the CS signal channel.added bu duwei 03/21/2003 */#define PESEL_MASK	0x07#define CONV_MASK	0x0FFF   /* 12 bit conversion */#define PEN_IRQ_NUM	IRQ6_IRQ_NUM/*#define CS_DATA		PFDATA#define CS_PUEN		PFPUEN#define CS_DIR		PFDIR#define CS_SEL		PFSEL*///changed by duwei 03/21/2003#define CS_DATA		PGDATA#define CS_PUEN		PGPUEN#define CS_DIR		PGDIR#define CS_SEL		PGSEL//changed by liusen 07/09/2004//#define CS_DATA		PFDATA//#define CS_PUEN		PFPUEN//#define CS_DIR		PFDIR//#define CS_SEL		PFSEL#define PENIRQ_DATA 	PDDATA#define PENIRQ_PUEN	PDPUEN#define PENIRQ_DIR	PDDIR#define PENIRQ_SEL	PDSEL#define ICR_PENPOL	ICR_POL6#define IMR_MPEN	IMR_MIRQ6#else#error "unexpected"#define USE_PENIRQ_PULUP#define PEN_MASK	PF_IRQ5  /* pen irq signal from the Burr-Brown is */#define PEN_MASK_2	PD_IRQ1  /* connected to 2 pins of the DragonBall */                             /* (bit 2 port F and bit 4 port D)       */#define BUSY_MASK	PF_A22#define CS_MASK		PB_CSD0_CAS0#define PESEL_MASK	0x07#define CONV_MASK	0x0FFF   /* 12 bit conversion */#define PEN_IRQ_NUM	IRQ5_IRQ_NUM/* chip select register offset */#define CS_DATA		PBDATA#define CS_PUEN		PBPUEN#define CS_DIR		PBDIR#define CS_SEL		PBSEL/* pen irq register offsets and data */#define PENIRQ_DATA	PFDATA#define PENIRQ_PUEN	PFPUEN#define PENIRQ_DIR	PFDIR#define PENIRQ_SEL	PFSEL#define ICR_PENPOL	ICR_POL5#define IMR_MPEN	IMR_MIRQ5#endif/* * Touch screen driver states. */#define TS_DRV_ERROR       -1#define TS_DRV_IDLE         0#define TS_DRV_WAIT         1#define TS_DRV_ASKX         2#define TS_DRV_ASKY         3#define TS_DRV_READX        4#define TS_DRV_READY        5/* * Conversion status. */#define CONV_ERROR      -1   /* error during conversion flow        */    #define CONV_END         0   /* conversion ended (= pen is up)      */#define CONV_LOOP        1   /* conversion continue (= pen is down) *//*----------------------------------------------------------------------------*//* macros --------------------------------------------------------------------*/#define TICKS(nbms)        ((HZ*(nbms))/1000)/*----------------------------------------------------------------------------*//* * Look in the PF register if it is on interrupt state. */#ifdef CONFIG_XCOPILOT_BUGS# define IS_PEN_DOWN    ((IPR&IPR_PEN)!=0)#else# define IS_PEN_DOWN	((PENIRQ_DATA & PEN_MASK)==ST_PEN_DOWN)#endif/* * State of the BUSY signal of the SPIM. *///#define IS_BUSY_ENDED   ((PFDATA & BUSY_MASK)==0)//#define IS_BUSY_ENDED   ((PGDATA & BUSY_MASK)==0)  //changed by duwei 03/21/2003#define IS_BUSY_ENDED   ((PBDATA & BUSY_MASK)==0)  //changed by duwei 07/2/2003

⌨️ 快捷键说明

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