OSDN Git Service

change device driver to push 128 data at once
[fpga-leon-mjpeg/leon-mjpeg.git] / snapgear-2.6-p42 / linux-2.6.21.1 / drivers / kmjpeg / kmjpeg.c
1 #include <linux/init.h>
2 #include <linux/module.h>
3 #include <linux/types.h>
4 #include <linux/kernel.h>
5 #include <linux/fs.h>
6 #include <linux/cdev.h>
7 #include <linux/sched.h>
8 #include <asm/current.h>
9 #include <asm/uaccess.h>
10 #include <asm/io.h>
11
12 #include <linux/io.h>
13 #include <linux/ioport.h>
14
15 #include <linux/interrupt.h>
16 #include <linux/fcntl.h>
17 #include <linux/slab.h>
18
19 #include "kmjpeg.h"
20
21 MODULE_LICENSE("GPL");
22
23 #define DRIVER_NAME "kmjpeg"
24
25
26 #define AHBADD 0xa0000000
27 #define RDYADD 0xa0000200
28 #define APBADD 0x80000c00
29
30
31 /* Physical address for NEEK
32 #define AHBADD 0xb0000000
33 #define RDYADD 0xb0000200
34 #define APBADD 0x80000700
35 */
36
37 static struct kmjpeg_priv *kmjpeg_devices;
38
39 static unsigned int kmjpeg_major = 0;
40 module_param(kmjpeg_major, uint, 0);
41
42 struct kmjpeg_sregs_t {
43   volatile unsigned int fbadd;
44   volatile unsigned int size_info;
45   volatile unsigned int inc_add;
46   volatile unsigned int reset;
47 };
48
49 struct kmjpeg_sregs_t * kmjpeg_sregs;
50
51 //volatile unsigned int *apb_regs;
52
53 volatile unsigned int *hdata;
54 volatile unsigned int *rdyadd;
55
56 int kmjpeg_ioctl(struct inode *inode, struct file *filep, unsigned int cmd, unsigned long arg)
57 {
58   int retval = 0;
59  
60   struct ioctl_cmdreg datareg;
61   struct ioctl_cmdwrite datawrite;
62
63   unsigned int tmp;
64   int i;
65
66   memset(&datareg, 0, sizeof(datareg));
67   memset(&datawrite, 0, sizeof(datawrite));
68
69
70   retval = 0;
71   switch(cmd){
72
73   case IOCTL_WRITE :
74    if(!access_ok(VERIFY_READ, (void __user *)arg, _IOC_SIZE(cmd))){
75       retval = -EFAULT;
76       goto done;
77    }
78    if(copy_from_user(&datawrite, (int __user *)arg, sizeof(datawrite))){
79       retval = -EFAULT;
80       goto done;
81    }
82    
83    while(1){
84      tmp = *rdyadd;
85      if((tmp & 0x80000000) == 0x80000000)break;
86      for(i=0;i<800;i++);
87    }
88    //  *hdata = datawrite.pixeldata;
89    for(i=0;i<128;i++){
90      *hdata = datawrite.fourbdata[i];
91    }
92    break;
93   
94   case IOCTL_REGSET :
95     //    printk("IOCTL_REGSET\n");
96    if(!access_ok(VERIFY_READ, (void __user *)arg, _IOC_SIZE(cmd))){
97       retval = -EFAULT;
98       printk("ACCESS_NG\n");
99       goto done;
100     }
101    //   printk("end of access_ok\n");
102     if(copy_from_user(&datareg, (int __user *)arg, sizeof(datareg))){
103       retval = -EFAULT;
104       printk("COPY_NG\n");
105       goto done;
106     }
107     //    printk("IOCTL regset ..............................\n");
108     kmjpeg_sregs = ioremap_nocache(APBADD,12);
109     //   printk("IOCTL regset2 ..............................\n");
110     kmjpeg_sregs->fbadd = datareg.fb;
111     kmjpeg_sregs->size_info = datareg.size_info;
112     kmjpeg_sregs->inc_add = datareg.inc_add;
113     kmjpeg_sregs->reset = 0x0;
114     kmjpeg_sregs->reset =0xffffffff;
115     iounmap(kmjpeg_sregs);
116     //    printk("IOCTL regset3 ..............................\n");
117  
118     break;
119  
120   default :
121     retval = -EFAULT;
122     break;
123   }
124  done :
125   return(retval);
126 }
127
128 ssize_t kmjpeg_write(struct file *filp, const char __user *buf, size_t count, loff_t *f_pos)
129 {
130   int retval = 0;
131   unsigned int ycc;
132   unsigned char dbuf[3];
133
134   if(count != 3){
135     retval = -EFAULT;
136     goto out;
137   }
138   if(copy_from_user(dbuf, buf, 3)){
139     retval = -EFAULT;
140     goto out;
141   }
142   ycc = (unsigned int)(((unsigned int)dbuf[2]<<16)|((unsigned int)dbuf[1]<<8)|((unsigned int)dbuf[0]));
143   *hdata = ycc;
144   retval = count;
145  out:
146   return(retval);
147
148
149 static ssize_t kmjpeg_read(struct file* pFile, char __user* pBuf, size_t len, loff_t* offset)
150 {
151    return 0;
152 }
153
154
155
156
157 static int kmjpeg_open(struct inode *inode, struct file *file)
158 {
159    
160   printk("%s: major %d minor %d (pid %d)\n", __func__,imajor(inode),iminor(inode),current->pid);
161  
162   inode->i_private = inode;
163   file->private_data = file;
164   printk(" i_private=%p private_data=%p\n",inode->i_private, file->private_data);
165   //  printk("kmjpeg_open ending\n");
166   return 0;
167 }
168
169 static int kmjpeg_close(struct inode *inode, struct file *file)
170 {
171   printk("%s: major %d minor %d (pid %d)\n", __func__,imajor(inode),iminor(inode),current->pid);
172   printk(" i_private=%p private_data=%p\n",inode->i_private, file->private_data);
173
174   return 0;
175 }
176
177 struct file_operations kmjpeg_fops ={
178   .owner = THIS_MODULE,
179   .open = kmjpeg_open,
180   .release = kmjpeg_close,
181   .read = kmjpeg_read,
182   .write = kmjpeg_write,
183   .ioctl = kmjpeg_ioctl,
184 };
185
186  static int kmjpeg_init(void)
187 {
188   int major;
189   int ret = 0;
190
191   major = register_chrdev(kmjpeg_major, DRIVER_NAME, &kmjpeg_fops);
192
193   if((kmjpeg_major > 0 && major != 0) || (kmjpeg_major == 0 && major < 0) || major < 0){
194     printk("%s driver registration error\n", DRIVER_NAME);
195     ret = major;
196     goto error;
197   }
198   if (kmjpeg_major == 0){
199     kmjpeg_major = major;
200   }
201
202   hdata = ioremap_nocache(AHBADD,4);
203   if(hdata==NULL){
204     printk("ioremap miss!\n");
205     return(0);
206   }
207   rdyadd = ioremap_nocache(RDYADD,4);
208   if(rdyadd==NULL){
209     printk("ioremap miss!\n");
210     return(0);
211   }
212   printk("%s driver[major %d] installed.\n", DRIVER_NAME, kmjpeg_major);
213
214  error:
215   return(ret);
216 }
217
218 static void kmjpeg_exit(void)
219 {
220   iounmap(hdata);
221   iounmap(rdyadd);
222   //  kfree(kmjpeg_devices);
223
224   unregister_chrdev(kmjpeg_major, DRIVER_NAME);
225   printk("%s driver unloaded\n", DRIVER_NAME);
226 }
227
228 module_init(kmjpeg_init);
229 module_exit(kmjpeg_exit);