import of ftp.dlink.com/GPL/DSMG-600_reB/ppclinux.tar.gz
[linux-2.4.21-pre4.git] / drivers / media / video / meye.c
1 /* 
2  * Motion Eye video4linux driver for Sony Vaio PictureBook
3  *
4  * Copyright (C) 2001-2002 Stelian Pop <stelian@popies.net>
5  *
6  * Copyright (C) 2001-2002 AlcĂ´ve <www.alcove.com>
7  *
8  * Copyright (C) 2000 Andrew Tridgell <tridge@valinux.com>
9  *
10  * Earlier work by Werner Almesberger, Paul `Rusty' Russell and Paul Mackerras.
11  *
12  * Some parts borrowed from various video4linux drivers, especially
13  * bttv-driver.c and zoran.c, see original files for credits.
14  * 
15  * This program is free software; you can redistribute it and/or modify
16  * it under the terms of the GNU General Public License as published by
17  * the Free Software Foundation; either version 2 of the License, or
18  * (at your option) any later version.
19  * 
20  * This program is distributed in the hope that it will be useful,
21  * but WITHOUT ANY WARRANTY; without even the implied warranty of
22  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23  * GNU General Public License for more details.
24  * 
25  * You should have received a copy of the GNU General Public License
26  * along with this program; if not, write to the Free Software
27  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
28  */
29 #include <linux/config.h>
30 #include <linux/module.h>
31 #include <linux/pci.h>
32 #include <linux/sched.h>
33 #include <linux/init.h>
34 #include <linux/videodev.h>
35 #include <asm/uaccess.h>
36 #include <asm/io.h>
37 #include <linux/delay.h>
38 #include <linux/wrapper.h>
39 #include <linux/interrupt.h>
40 #include <linux/vmalloc.h>
41
42 #include "meye.h"
43 #include "linux/meye.h"
44
45 /* driver structure - only one possible */
46 static struct meye meye;
47 /* number of grab buffers */
48 static unsigned int gbuffers = 2;
49 /* size of a grab buffer */
50 static unsigned int gbufsize = MEYE_MAX_BUFSIZE;
51 /* /dev/videoX registration number */
52 static int video_nr = -1;
53
54 /****************************************************************************/
55 /* Queue routines                                                           */
56 /****************************************************************************/
57
58 /* Inits the queue */
59 static inline void meye_initq(struct meye_queue *queue) {
60         queue->head = queue->tail = 0;
61         queue->len = 0;
62         queue->s_lock = (spinlock_t)SPIN_LOCK_UNLOCKED;
63         init_waitqueue_head(&queue->proc_list);
64 }
65
66 /* Pulls an element from the queue */
67 static inline int meye_pullq(struct meye_queue *queue) {
68         int result;
69         unsigned long flags;
70
71         spin_lock_irqsave(&queue->s_lock, flags);
72         if (!queue->len) {
73                 spin_unlock_irqrestore(&queue->s_lock, flags);
74                 return -1;
75         }
76         result = queue->buf[queue->head];
77         queue->head++;
78         queue->head &= (MEYE_QUEUE_SIZE - 1);
79         queue->len--;
80         spin_unlock_irqrestore(&queue->s_lock, flags);
81         return result;
82 }
83
84 /* Pushes an element into the queue */
85 static inline void meye_pushq(struct meye_queue *queue, int element) {
86         unsigned long flags;
87
88         spin_lock_irqsave(&queue->s_lock, flags);
89         if (queue->len == MEYE_QUEUE_SIZE) {
90                 /* remove the first element */
91                 queue->head++;
92                 queue->head &= (MEYE_QUEUE_SIZE - 1);
93                 queue->len--;
94         }
95         queue->buf[queue->tail] = element;
96         queue->tail++;
97         queue->tail &= (MEYE_QUEUE_SIZE - 1);
98         queue->len++;
99
100         spin_unlock_irqrestore(&queue->s_lock, flags);
101 }
102
103 /* Tests if the queue is empty */
104 static inline int meye_emptyq(struct meye_queue *queue, int *elem) {
105         int result;
106         unsigned long flags;
107
108         spin_lock_irqsave(&queue->s_lock, flags);
109         result = (queue->len == 0);
110         if (!result && elem)
111                 *elem = queue->buf[queue->head];
112         spin_unlock_irqrestore(&queue->s_lock, flags);
113         return result;
114 }
115
116 /****************************************************************************/
117 /* Memory allocation routines (stolen from bttv-driver.c)                   */
118 /****************************************************************************/
119
120 /* Here we want the physical address of the memory.
121  * This is used when initializing the contents of the area.
122  */
123 static inline unsigned long kvirt_to_pa(unsigned long adr) {
124         unsigned long kva, ret;
125
126         kva = (unsigned long) page_address(vmalloc_to_page((void *)adr));
127         kva |= adr & (PAGE_SIZE-1); /* restore the offset */
128         ret = __pa(kva);
129         return ret;
130 }
131
132 static void *rvmalloc(unsigned long size) {
133         void *mem;
134         unsigned long adr;
135
136         size = PAGE_ALIGN(size);
137         mem = vmalloc_32(size);
138         if (mem) {
139                 memset(mem, 0, size); /* Clear the ram out, no junk to the user */
140                 adr = (unsigned long)mem;
141                 while (size > 0) {
142                         mem_map_reserve(vmalloc_to_page((void *)adr));
143                         adr += PAGE_SIZE;
144                         size -= PAGE_SIZE;
145                 }
146         }
147         return mem;
148 }
149
150 static void rvfree(void * mem, unsigned long size) {
151         unsigned long adr;
152
153         if (mem) {
154                 adr = (unsigned long) mem;
155                 while ((long) size > 0) {
156                         mem_map_unreserve(vmalloc_to_page((void *)adr));
157                         adr += PAGE_SIZE;
158                         size -= PAGE_SIZE;
159                 }
160                 vfree(mem);
161         }
162 }
163
164 /* return a page table pointing to N pages of locked memory */
165 static int ptable_alloc(void) {
166         u32 *pt;
167         int i;
168
169         memset(meye.mchip_ptable, 0, sizeof(meye.mchip_ptable));
170
171         meye.mchip_ptable[MCHIP_NB_PAGES] = pci_alloc_consistent(meye.mchip_dev, 
172                                                                  PAGE_SIZE, 
173                                                                  &meye.mchip_dmahandle);
174         if (!meye.mchip_ptable[MCHIP_NB_PAGES]) {
175                 meye.mchip_dmahandle = 0;
176                 return -1;
177         }
178
179         pt = (u32 *)meye.mchip_ptable[MCHIP_NB_PAGES];
180         for (i = 0; i < MCHIP_NB_PAGES; i++) {
181                 meye.mchip_ptable[i] = pci_alloc_consistent(meye.mchip_dev, 
182                                                             PAGE_SIZE,
183                                                             pt);
184                 if (!meye.mchip_ptable[i]) {
185                         int j;
186                         pt = (u32 *)meye.mchip_ptable[MCHIP_NB_PAGES];
187                         for (j = 0; j < i; ++j) {
188                                 pci_free_consistent(meye.mchip_dev,
189                                                     PAGE_SIZE,
190                                                     meye.mchip_ptable[j], *pt);
191                                 pt++;
192                         }
193                         meye.mchip_dmahandle = 0;
194                         return -1;
195                 }
196                 pt++;
197         }
198         return 0;
199 }
200
201 static void ptable_free(void) {
202         u32 *pt;
203         int i;
204
205         pt = (u32 *)meye.mchip_ptable[MCHIP_NB_PAGES];
206         for (i = 0; i < MCHIP_NB_PAGES; i++) {
207                 if (meye.mchip_ptable[i])
208                         pci_free_consistent(meye.mchip_dev, 
209                                             PAGE_SIZE, 
210                                             meye.mchip_ptable[i], *pt);
211                 pt++;
212         }
213
214         if (meye.mchip_ptable[MCHIP_NB_PAGES])
215                 pci_free_consistent(meye.mchip_dev, 
216                                     PAGE_SIZE, 
217                                     meye.mchip_ptable[MCHIP_NB_PAGES], 
218                                     meye.mchip_dmahandle);
219
220         memset(meye.mchip_ptable, 0, sizeof(meye.mchip_ptable));
221         meye.mchip_dmahandle = 0;
222 }
223
224 /* copy data from ptable into buf */
225 static void ptable_copy(u8 *buf, int start, int size, int pt_pages) {
226         int i;
227         
228         for (i = 0; i < (size / PAGE_SIZE) * PAGE_SIZE; i += PAGE_SIZE) {
229                 memcpy(buf + i, meye.mchip_ptable[start++], PAGE_SIZE);
230                 if (start >= pt_pages)
231                         start = 0;
232         }
233         memcpy(buf + i, meye.mchip_ptable[start], size % PAGE_SIZE);
234 }
235
236
237 /****************************************************************************/
238 /* JPEG tables at different qualities to load into the VRJ chip             */
239 /****************************************************************************/
240
241 /* return a set of quantisation tables based on a quality from 1 to 10 */
242 static u16 *jpeg_quantisation_tables(int *size, int quality) {
243         static u16 tables0[] = {
244                 0xdbff, 0x4300, 0xff00, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
245                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
246                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
247                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
248                 0xffff, 0xffff, 0xffff, 
249                 0xdbff, 0x4300, 0xff01, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
250                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
251                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
252                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
253                 0xffff, 0xffff, 0xffff, 
254         };
255         static u16 tables1[] = {
256                 0xdbff, 0x4300, 0x5000, 0x3c37, 0x3c46, 0x5032, 0x4146, 0x5a46, 
257                 0x5055, 0x785f, 0x82c8, 0x6e78, 0x786e, 0xaff5, 0x91b9, 0xffc8, 
258                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
259                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
260                 0xffff, 0xffff, 0xffff, 
261                 0xdbff, 0x4300, 0x5501, 0x5a5a, 0x6978, 0xeb78, 0x8282, 0xffeb, 
262                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
263                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
264                 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff, 
265                 0xffff, 0xffff, 0xffff, 
266         };
267         static u16 tables2[] = {
268                 0xdbff, 0x4300, 0x2800, 0x1e1c, 0x1e23, 0x2819, 0x2123, 0x2d23, 
269                 0x282b, 0x3c30, 0x4164, 0x373c, 0x3c37, 0x587b, 0x495d, 0x9164, 
270                 0x9980, 0x8f96, 0x8c80, 0xa08a, 0xe6b4, 0xa0c3, 0xdaaa, 0x8aad, 
271                 0xc88c, 0xcbff, 0xeeda, 0xfff5, 0xffff, 0xc19b, 0xffff, 0xfaff, 
272                 0xe6ff, 0xfffd, 0xfff8, 
273                 0xdbff, 0x4300, 0x2b01, 0x2d2d, 0x353c, 0x763c, 0x4141, 0xf876, 
274                 0x8ca5, 0xf8a5, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 
275                 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 
276                 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 0xf8f8, 
277                 0xf8f8, 0xf8f8, 0xfff8, 
278         };
279         static u16 tables3[] = {
280                 0xdbff, 0x4300, 0x1b00, 0x1412, 0x1417, 0x1b11, 0x1617, 0x1e17, 
281                 0x1b1c, 0x2820, 0x2b42, 0x2528, 0x2825, 0x3a51, 0x303d, 0x6042, 
282                 0x6555, 0x5f64, 0x5d55, 0x6a5b, 0x9978, 0x6a81, 0x9071, 0x5b73, 
283                 0x855d, 0x86b5, 0x9e90, 0xaba3, 0xabad, 0x8067, 0xc9bc, 0xa6ba, 
284                 0x99c7, 0xaba8, 0xffa4, 
285                 0xdbff, 0x4300, 0x1c01, 0x1e1e, 0x2328, 0x4e28, 0x2b2b, 0xa44e, 
286                 0x5d6e, 0xa46e, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 
287                 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 
288                 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 0xa4a4, 
289                 0xa4a4, 0xa4a4, 0xffa4, 
290         };
291         static u16 tables4[] = {
292                 0xdbff, 0x4300, 0x1400, 0x0f0e, 0x0f12, 0x140d, 0x1012, 0x1712, 
293                 0x1415, 0x1e18, 0x2132, 0x1c1e, 0x1e1c, 0x2c3d, 0x242e, 0x4932, 
294                 0x4c40, 0x474b, 0x4640, 0x5045, 0x735a, 0x5062, 0x6d55, 0x4556, 
295                 0x6446, 0x6588, 0x776d, 0x817b, 0x8182, 0x604e, 0x978d, 0x7d8c, 
296                 0x7396, 0x817e, 0xff7c, 
297                 0xdbff, 0x4300, 0x1501, 0x1717, 0x1a1e, 0x3b1e, 0x2121, 0x7c3b, 
298                 0x4653, 0x7c53, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 
299                 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 
300                 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 0x7c7c, 
301                 0x7c7c, 0x7c7c, 0xff7c, 
302         };
303         static u16 tables5[] = {
304                 0xdbff, 0x4300, 0x1000, 0x0c0b, 0x0c0e, 0x100a, 0x0d0e, 0x120e, 
305                 0x1011, 0x1813, 0x1a28, 0x1618, 0x1816, 0x2331, 0x1d25, 0x3a28, 
306                 0x3d33, 0x393c, 0x3833, 0x4037, 0x5c48, 0x404e, 0x5744, 0x3745, 
307                 0x5038, 0x516d, 0x5f57, 0x6762, 0x6768, 0x4d3e, 0x7971, 0x6470, 
308                 0x5c78, 0x6765, 0xff63, 
309                 0xdbff, 0x4300, 0x1101, 0x1212, 0x1518, 0x2f18, 0x1a1a, 0x632f, 
310                 0x3842, 0x6342, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 
311                 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 
312                 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 0x6363, 
313                 0x6363, 0x6363, 0xff63, 
314         };
315         static u16 tables6[] = {
316                 0xdbff, 0x4300, 0x0d00, 0x0a09, 0x0a0b, 0x0d08, 0x0a0b, 0x0e0b, 
317                 0x0d0e, 0x130f, 0x1520, 0x1213, 0x1312, 0x1c27, 0x171e, 0x2e20, 
318                 0x3129, 0x2e30, 0x2d29, 0x332c, 0x4a3a, 0x333e, 0x4636, 0x2c37, 
319                 0x402d, 0x4157, 0x4c46, 0x524e, 0x5253, 0x3e32, 0x615a, 0x505a, 
320                 0x4a60, 0x5251, 0xff4f, 
321                 0xdbff, 0x4300, 0x0e01, 0x0e0e, 0x1113, 0x2613, 0x1515, 0x4f26, 
322                 0x2d35, 0x4f35, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 
323                 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 
324                 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 0x4f4f, 
325                 0x4f4f, 0x4f4f, 0xff4f, 
326         };
327         static u16 tables7[] = {
328                 0xdbff, 0x4300, 0x0a00, 0x0707, 0x0708, 0x0a06, 0x0808, 0x0b08, 
329                 0x0a0a, 0x0e0b, 0x1018, 0x0d0e, 0x0e0d, 0x151d, 0x1116, 0x2318, 
330                 0x251f, 0x2224, 0x221f, 0x2621, 0x372b, 0x262f, 0x3429, 0x2129, 
331                 0x3022, 0x3141, 0x3934, 0x3e3b, 0x3e3e, 0x2e25, 0x4944, 0x3c43, 
332                 0x3748, 0x3e3d, 0xff3b, 
333                 0xdbff, 0x4300, 0x0a01, 0x0b0b, 0x0d0e, 0x1c0e, 0x1010, 0x3b1c, 
334                 0x2228, 0x3b28, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 
335                 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 
336                 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 0x3b3b, 
337                 0x3b3b, 0x3b3b, 0xff3b, 
338         };
339         static u16 tables8[] = {
340                 0xdbff, 0x4300, 0x0600, 0x0504, 0x0506, 0x0604, 0x0506, 0x0706, 
341                 0x0607, 0x0a08, 0x0a10, 0x090a, 0x0a09, 0x0e14, 0x0c0f, 0x1710, 
342                 0x1814, 0x1718, 0x1614, 0x1a16, 0x251d, 0x1a1f, 0x231b, 0x161c, 
343                 0x2016, 0x202c, 0x2623, 0x2927, 0x292a, 0x1f19, 0x302d, 0x282d, 
344                 0x2530, 0x2928, 0xff28, 
345                 0xdbff, 0x4300, 0x0701, 0x0707, 0x080a, 0x130a, 0x0a0a, 0x2813, 
346                 0x161a, 0x281a, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 
347                 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 
348                 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 0x2828, 
349                 0x2828, 0x2828, 0xff28, 
350         };
351         static u16 tables9[] = {
352                 0xdbff, 0x4300, 0x0300, 0x0202, 0x0203, 0x0302, 0x0303, 0x0403, 
353                 0x0303, 0x0504, 0x0508, 0x0405, 0x0504, 0x070a, 0x0607, 0x0c08, 
354                 0x0c0a, 0x0b0c, 0x0b0a, 0x0d0b, 0x120e, 0x0d10, 0x110e, 0x0b0e, 
355                 0x100b, 0x1016, 0x1311, 0x1514, 0x1515, 0x0f0c, 0x1817, 0x1416, 
356                 0x1218, 0x1514, 0xff14, 
357                 0xdbff, 0x4300, 0x0301, 0x0404, 0x0405, 0x0905, 0x0505, 0x1409, 
358                 0x0b0d, 0x140d, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 
359                 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 
360                 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 0x1414, 
361                 0x1414, 0x1414, 0xff14, 
362         };
363         static u16 tables10[] = {
364                 0xdbff, 0x4300, 0x0100, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
365                 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
366                 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
367                 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
368                 0x0101, 0x0101, 0xff01, 
369                 0xdbff, 0x4300, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
370                 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
371                 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
372                 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 0x0101, 
373                 0x0101, 0x0101, 0xff01, 
374         };
375
376         switch (quality) {
377         case 0:
378                 *size = sizeof(tables0);
379                 return tables0;
380         case 1:
381                 *size = sizeof(tables1);
382                 return tables1;
383         case 2:
384                 *size = sizeof(tables2);
385                 return tables2;
386         case 3:
387                 *size = sizeof(tables3);
388                 return tables3;
389         case 4:
390                 *size = sizeof(tables4);
391                 return tables4;
392         case 5:
393                 *size = sizeof(tables5);
394                 return tables5;
395         case 6:
396                 *size = sizeof(tables6);
397                 return tables6;
398         case 7:
399                 *size = sizeof(tables7);
400                 return tables7;
401         case 8:
402                 *size = sizeof(tables8);
403                 return tables8;
404         case 9:
405                 *size = sizeof(tables9);
406                 return tables9;
407         case 10:
408                 *size = sizeof(tables10);
409                 return tables10;
410         default:
411                 printk(KERN_WARNING "meye: invalid quality level %d - using 8\n", quality);
412                 *size = sizeof(tables8);
413                 return tables8;
414         }
415         return NULL;
416 }
417
418 /* return a generic set of huffman tables */
419 static u16 *jpeg_huffman_tables(int *size) {
420         static u16 tables[] = {
421                 0xC4FF, 0xB500, 0x0010, 0x0102, 0x0303, 0x0402, 0x0503, 0x0405, 
422                 0x0004, 0x0100, 0x017D, 0x0302, 0x0400, 0x0511, 0x2112, 0x4131, 
423                 0x1306, 0x6151, 0x2207, 0x1471, 0x8132, 0xA191, 0x2308, 0xB142, 
424                 0x15C1, 0xD152, 0x24F0, 0x6233, 0x8272, 0x0A09, 0x1716, 0x1918, 
425                 0x251A, 0x2726, 0x2928, 0x342A, 0x3635, 0x3837, 0x3A39, 0x4443, 
426                 0x4645, 0x4847, 0x4A49, 0x5453, 0x5655, 0x5857, 0x5A59, 0x6463, 
427                 0x6665, 0x6867, 0x6A69, 0x7473, 0x7675, 0x7877, 0x7A79, 0x8483, 
428                 0x8685, 0x8887, 0x8A89, 0x9392, 0x9594, 0x9796, 0x9998, 0xA29A, 
429                 0xA4A3, 0xA6A5, 0xA8A7, 0xAAA9, 0xB3B2, 0xB5B4, 0xB7B6, 0xB9B8, 
430                 0xC2BA, 0xC4C3, 0xC6C5, 0xC8C7, 0xCAC9, 0xD3D2, 0xD5D4, 0xD7D6, 
431                 0xD9D8, 0xE1DA, 0xE3E2, 0xE5E4, 0xE7E6, 0xE9E8, 0xF1EA, 0xF3F2, 
432                 0xF5F4, 0xF7F6, 0xF9F8, 0xFFFA, 
433                 0xC4FF, 0xB500, 0x0011, 0x0102, 0x0402, 0x0304, 0x0704, 0x0405, 
434                 0x0004, 0x0201, 0x0077, 0x0201, 0x1103, 0x0504, 0x3121, 0x1206, 
435                 0x5141, 0x6107, 0x1371, 0x3222, 0x0881, 0x4214, 0xA191, 0xC1B1, 
436                 0x2309, 0x5233, 0x15F0, 0x7262, 0x0AD1, 0x2416, 0xE134, 0xF125, 
437                 0x1817, 0x1A19, 0x2726, 0x2928, 0x352A, 0x3736, 0x3938, 0x433A, 
438                 0x4544, 0x4746, 0x4948, 0x534A, 0x5554, 0x5756, 0x5958, 0x635A, 
439                 0x6564, 0x6766, 0x6968, 0x736A, 0x7574, 0x7776, 0x7978, 0x827A, 
440                 0x8483, 0x8685, 0x8887, 0x8A89, 0x9392, 0x9594, 0x9796, 0x9998, 
441                 0xA29A, 0xA4A3, 0xA6A5, 0xA8A7, 0xAAA9, 0xB3B2, 0xB5B4, 0xB7B6, 
442                 0xB9B8, 0xC2BA, 0xC4C3, 0xC6C5, 0xC8C7, 0xCAC9, 0xD3D2, 0xD5D4, 
443                 0xD7D6, 0xD9D8, 0xE2DA, 0xE4E3, 0xE6E5, 0xE8E7, 0xEAE9, 0xF3F2, 
444                 0xF5F4, 0xF7F6, 0xF9F8, 0xFFFA, 
445                 0xC4FF, 0x1F00, 0x0000, 0x0501, 0x0101, 0x0101, 0x0101, 0x0000, 
446                 0x0000, 0x0000, 0x0000, 0x0201, 0x0403, 0x0605, 0x0807, 0x0A09, 
447                 0xFF0B, 
448                 0xC4FF, 0x1F00, 0x0001, 0x0103, 0x0101, 0x0101, 0x0101, 0x0101, 
449                 0x0000, 0x0000, 0x0000, 0x0201, 0x0403, 0x0605, 0x0807, 0x0A09, 
450                 0xFF0B
451         };
452
453         *size = sizeof(tables);
454         return tables;
455 }
456
457 /****************************************************************************/
458 /* MCHIP low-level functions                                                */
459 /****************************************************************************/
460
461 /* waits for the specified miliseconds */
462 static inline void wait_ms(unsigned int ms) {
463         if (!in_interrupt()) {
464                 set_current_state(TASK_UNINTERRUPTIBLE);
465                 schedule_timeout(1 + ms * HZ / 1000);
466         }
467         else
468                 mdelay(ms);
469 }
470
471 /* returns the horizontal capture size */
472 static inline int mchip_hsize(void) {
473         return meye.params.subsample ? 320 : 640;
474 }
475
476 /* returns the vertical capture size */
477 static inline int mchip_vsize(void) {
478         return meye.params.subsample ? 240 : 480;
479 }
480
481 /* waits for a register to be available */
482 static void mchip_sync(int reg) {
483         u32 status;
484         int i;
485
486         if (reg == MCHIP_MM_FIFO_DATA) {
487                 for (i = 0; i < MCHIP_REG_TIMEOUT; i++) {
488                         status = readl(meye.mchip_mmregs + MCHIP_MM_FIFO_STATUS);
489                         if (!(status & MCHIP_MM_FIFO_WAIT)) {
490                                 printk(KERN_WARNING "meye: fifo not ready\n");
491                                 return;
492                         }
493                         if (status & MCHIP_MM_FIFO_READY)
494                                 return;
495                         udelay(1);
496                 }
497         }
498         else if (reg > 0x80) {
499                 u32 mask = (reg < 0x100) ? MCHIP_HIC_STATUS_MCC_RDY
500                                          : MCHIP_HIC_STATUS_VRJ_RDY;
501                 for (i = 0; i < MCHIP_REG_TIMEOUT; i++) {
502                         status = readl(meye.mchip_mmregs + MCHIP_HIC_STATUS);
503                         if (status & mask)
504                                 return;
505                         udelay(1);
506                 }
507         }
508         else
509                 return;
510         printk(KERN_WARNING "meye: mchip_sync() timeout on reg 0x%x status=0x%x\n", reg, status);
511 }
512
513 /* sets a value into the register */
514 static inline void mchip_set(int reg, u32 v) {
515         mchip_sync(reg);
516         writel(v, meye.mchip_mmregs + reg);
517 }
518
519 /* get the register value */
520 static inline u32 mchip_read(int reg) {
521         mchip_sync(reg);
522         return readl(meye.mchip_mmregs + reg);
523 }
524
525 /* wait for a register to become a particular value */
526 static inline int mchip_delay(u32 reg, u32 v) {
527         int n = 10;
528         while (--n && mchip_read(reg) != v) 
529                 udelay(1);
530         return n;
531 }
532
533 /* setup subsampling */
534 static void mchip_subsample(void) {
535         mchip_set(MCHIP_MCC_R_SAMPLING, meye.params.subsample);
536         mchip_set(MCHIP_MCC_R_XRANGE, mchip_hsize());
537         mchip_set(MCHIP_MCC_R_YRANGE, mchip_vsize());
538         mchip_set(MCHIP_MCC_B_XRANGE, mchip_hsize());
539         mchip_set(MCHIP_MCC_B_YRANGE, mchip_vsize());
540         mchip_delay(MCHIP_HIC_STATUS, MCHIP_HIC_STATUS_IDLE);
541 }
542
543 /* set the framerate into the mchip */
544 static void mchip_set_framerate(void) {
545         mchip_set(MCHIP_HIC_S_RATE, meye.params.framerate);
546 }
547
548 /* load some huffman and quantisation tables into the VRJ chip ready
549    for JPEG compression */
550 static void mchip_load_tables(void) {
551         int i;
552         int size;
553         u16 *tables;
554
555         tables = jpeg_huffman_tables(&size);
556         for (i = 0; i < size / 2; i++)
557                 writel(tables[i], meye.mchip_mmregs + MCHIP_VRJ_TABLE_DATA);
558
559         tables = jpeg_quantisation_tables(&size, meye.params.quality);
560         for (i = 0; i < size / 2; i++)
561                 writel(tables[i], meye.mchip_mmregs + MCHIP_VRJ_TABLE_DATA);
562 }
563
564 /* setup the VRJ parameters in the chip */
565 static void mchip_vrj_setup(u8 mode) {
566
567         mchip_set(MCHIP_VRJ_BUS_MODE, 5);
568         mchip_set(MCHIP_VRJ_SIGNAL_ACTIVE_LEVEL, 0x1f);
569         mchip_set(MCHIP_VRJ_PDAT_USE, 1);
570         mchip_set(MCHIP_VRJ_IRQ_FLAG, 0xa0);
571         mchip_set(MCHIP_VRJ_MODE_SPECIFY, mode);
572         mchip_set(MCHIP_VRJ_NUM_LINES, mchip_vsize());
573         mchip_set(MCHIP_VRJ_NUM_PIXELS, mchip_hsize());
574         mchip_set(MCHIP_VRJ_NUM_COMPONENTS, 0x1b);
575         mchip_set(MCHIP_VRJ_LIMIT_COMPRESSED_LO, 0xFFFF);
576         mchip_set(MCHIP_VRJ_LIMIT_COMPRESSED_HI, 0xFFFF);
577         mchip_set(MCHIP_VRJ_COMP_DATA_FORMAT, 0xC);
578         mchip_set(MCHIP_VRJ_RESTART_INTERVAL, 0);
579         mchip_set(MCHIP_VRJ_SOF1, 0x601);
580         mchip_set(MCHIP_VRJ_SOF2, 0x1502);
581         mchip_set(MCHIP_VRJ_SOF3, 0x1503);
582         mchip_set(MCHIP_VRJ_SOF4, 0x1596);
583         mchip_set(MCHIP_VRJ_SOS,  0x0ed0);
584
585         mchip_load_tables();
586 }
587
588 /* sets the DMA parameters into the chip */
589 static void mchip_dma_setup(u32 dma_addr) {
590         int i;
591
592         mchip_set(MCHIP_MM_PT_ADDR, dma_addr);
593         for (i = 0; i < 4; i++)
594                 mchip_set(MCHIP_MM_FIR(i), 0);
595         meye.mchip_fnum = 0;
596 }
597
598 /* setup for DMA transfers - also zeros the framebuffer */
599 static int mchip_dma_alloc(void) {
600         if (!meye.mchip_dmahandle)
601                 if (ptable_alloc())
602                         return -1;
603         return 0;
604 }
605
606 /* frees the DMA buffer */
607 static void mchip_dma_free(void) {
608         if (meye.mchip_dmahandle) {
609                 mchip_dma_setup(0);
610                 ptable_free();
611         }
612 }
613
614 /* stop any existing HIC action and wait for any dma to complete then
615    reset the dma engine */
616 static void mchip_hic_stop(void) {
617         int i = 0;
618
619         meye.mchip_mode = MCHIP_HIC_MODE_NOOP;
620         if (!(mchip_read(MCHIP_HIC_STATUS) & MCHIP_HIC_STATUS_BUSY)) 
621                 return;
622         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_STOP);
623         mchip_delay(MCHIP_HIC_CMD, 0);
624         while (!mchip_delay(MCHIP_HIC_STATUS, MCHIP_HIC_STATUS_IDLE)) {
625                 /*  resetting HIC */
626                 mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_STOP);
627                 mchip_delay(MCHIP_HIC_CMD, 0);
628                 mchip_set(MCHIP_HIC_CTL, MCHIP_HIC_CTL_SOFT_RESET);
629                 wait_ms(250);
630                 if (i++ > 20) {
631                         printk(KERN_ERR "meye: resetting HIC hanged!\n");
632                         break;
633                 }
634         }
635         wait_ms(100);
636 }
637
638 /****************************************************************************/
639 /* MCHIP frame processing functions                                         */
640 /****************************************************************************/
641
642 /* get the next ready frame from the dma engine */
643 static u32 mchip_get_frame(void) {
644         u32 v;
645         
646         v = mchip_read(MCHIP_MM_FIR(meye.mchip_fnum));
647         return v;
648 }
649
650 /* frees the current frame from the dma engine */
651 static void mchip_free_frame(void) {
652         mchip_set(MCHIP_MM_FIR(meye.mchip_fnum), 0);
653         meye.mchip_fnum++;
654         meye.mchip_fnum %= 4;
655 }
656
657 /* read one frame from the framebuffer assuming it was captured using
658    a uncompressed transfer */
659 static void mchip_cont_read_frame(u32 v, u8 *buf, int size) {
660         int pt_id;
661
662         pt_id = (v >> 17) & 0x3FF;
663
664         ptable_copy(buf, pt_id, size, MCHIP_NB_PAGES);
665
666 }
667
668 /* read a compressed frame from the framebuffer */
669 static int mchip_comp_read_frame(u32 v, u8 *buf, int size) {
670         int pt_start, pt_end, trailer;
671         int fsize;
672         int i;
673
674         pt_start = (v >> 19) & 0xFF;
675         pt_end = (v >> 11) & 0xFF;
676         trailer = (v >> 1) & 0x3FF;
677
678         if (pt_end < pt_start)
679                 fsize = (MCHIP_NB_PAGES_MJPEG - pt_start) * PAGE_SIZE +
680                         pt_end * PAGE_SIZE + trailer * 4;
681         else
682                 fsize = (pt_end - pt_start) * PAGE_SIZE + trailer * 4;
683
684         if (fsize > size) {
685                 printk(KERN_WARNING "meye: oversized compressed frame %d\n", 
686                        fsize);
687                 return -1;
688         }
689
690         ptable_copy(buf, pt_start, fsize, MCHIP_NB_PAGES_MJPEG);
691
692
693 #ifdef MEYE_JPEG_CORRECTION
694
695         /* Some mchip generated jpeg frames are incorrect. In most
696          * (all ?) of those cases, the final EOI (0xff 0xd9) marker 
697          * is not present at the end of the frame.
698          *
699          * Since adding the final marker is not enough to restore
700          * the jpeg integrity, we drop the frame.
701          */
702
703         for (i = fsize - 1; i > 0 && buf[i] == 0xff; i--) ;
704
705         if (i < 2 || buf[i - 1] != 0xff || buf[i] != 0xd9)
706                 return -1;
707
708 #endif
709
710         return fsize;
711 }
712
713 /* take a picture into SDRAM */
714 static void mchip_take_picture(void) {
715         int i;
716         
717         mchip_hic_stop();
718         mchip_subsample();
719         mchip_dma_setup(meye.mchip_dmahandle);
720
721         mchip_set(MCHIP_HIC_MODE, MCHIP_HIC_MODE_STILL_CAP);
722         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_START);
723
724         mchip_delay(MCHIP_HIC_CMD, 0);
725
726         for (i = 0; i < 100; ++i) {
727                 if (mchip_delay(MCHIP_HIC_STATUS, MCHIP_HIC_STATUS_IDLE))
728                         break;
729                 wait_ms(1);
730         }
731 }
732
733 /* dma a previously taken picture into a buffer */
734 static void mchip_get_picture(u8 *buf, int bufsize) {
735         u32 v;
736         int i;
737
738         mchip_set(MCHIP_HIC_MODE, MCHIP_HIC_MODE_STILL_OUT);
739         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_START);
740
741         mchip_delay(MCHIP_HIC_CMD, 0);
742         for (i = 0; i < 100; ++i) {
743                 if (mchip_delay(MCHIP_HIC_STATUS, MCHIP_HIC_STATUS_IDLE))
744                         break;
745                 wait_ms(1);
746         }
747         for (i = 0; i < 4 ; ++i) {
748                 v = mchip_get_frame();
749                 if (v & MCHIP_MM_FIR_RDY) {
750                         mchip_cont_read_frame(v, buf, bufsize);
751                         break;
752                 }
753                 mchip_free_frame();
754         }
755 }
756
757 /* start continuous dma capture */
758 static void mchip_continuous_start(void) {
759         mchip_hic_stop();
760         mchip_subsample();
761         mchip_set_framerate();
762         mchip_dma_setup(meye.mchip_dmahandle);
763
764         meye.mchip_mode = MCHIP_HIC_MODE_CONT_OUT;
765
766         mchip_set(MCHIP_HIC_MODE, MCHIP_HIC_MODE_CONT_OUT);
767         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_START);
768
769         mchip_delay(MCHIP_HIC_CMD, 0);
770 }
771
772 /* compress one frame into a buffer */
773 static int mchip_compress_frame(u8 *buf, int bufsize) {
774         u32 v;
775         int len = -1, i;
776
777         mchip_vrj_setup(0x3f);
778         udelay(50);
779
780         mchip_set(MCHIP_HIC_MODE, MCHIP_HIC_MODE_STILL_COMP);
781         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_START);
782         
783         mchip_delay(MCHIP_HIC_CMD, 0);
784         for (i = 0; i < 100; ++i) {
785                 if (mchip_delay(MCHIP_HIC_STATUS, MCHIP_HIC_STATUS_IDLE))
786                         break;
787                 wait_ms(1);
788         }
789
790         for (i = 0; i < 4 ; ++i) {
791                 v = mchip_get_frame();
792                 if (v & MCHIP_MM_FIR_RDY) {
793                         len = mchip_comp_read_frame(v, buf, bufsize);
794                         break;
795                 }
796                 mchip_free_frame();
797         }
798         return len;
799 }
800
801 #if 0
802 /* uncompress one image into a buffer */
803 static int mchip_uncompress_frame(u8 *img, int imgsize, u8 *buf, int bufsize) {
804         mchip_vrj_setup(0x3f);
805         udelay(50);
806
807         mchip_set(MCHIP_HIC_MODE, MCHIP_HIC_MODE_STILL_DECOMP);
808         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_START);
809         
810         mchip_delay(MCHIP_HIC_CMD, 0);
811
812         return mchip_comp_read_frame(buf, bufsize);
813 }
814 #endif
815
816 /* start continuous compressed capture */
817 static void mchip_cont_compression_start(void) {
818         mchip_hic_stop();
819         mchip_vrj_setup(0x3f);
820         mchip_subsample();
821         mchip_set_framerate();
822         mchip_dma_setup(meye.mchip_dmahandle);
823
824         meye.mchip_mode = MCHIP_HIC_MODE_CONT_COMP;
825
826         mchip_set(MCHIP_HIC_MODE, MCHIP_HIC_MODE_CONT_COMP);
827         mchip_set(MCHIP_HIC_CMD, MCHIP_HIC_CMD_START);
828
829         mchip_delay(MCHIP_HIC_CMD, 0);
830 }
831
832 /****************************************************************************/
833 /* Interrupt handling                                                       */
834 /****************************************************************************/
835
836 static void meye_irq(int irq, void *dev_id, struct pt_regs *regs) {
837         u32 v;
838         int reqnr;
839         v = mchip_read(MCHIP_MM_INTA);
840
841         while (1) {
842                 v = mchip_get_frame();
843                 if (!(v & MCHIP_MM_FIR_RDY))
844                         return;
845                 switch (meye.mchip_mode) {
846
847                 case MCHIP_HIC_MODE_CONT_OUT:
848                         if (!meye_emptyq(&meye.grabq, NULL)) {
849                                 int nr = meye_pullq(&meye.grabq);
850                                 mchip_cont_read_frame(
851                                         v, 
852                                         meye.grab_fbuffer + gbufsize * nr,
853                                         mchip_hsize() * mchip_vsize() * 2);
854                                 meye.grab_buffer[nr].state = MEYE_BUF_DONE;
855                                 wake_up_interruptible(&meye.grabq.proc_list);
856                         }
857                         break;
858
859                 case MCHIP_HIC_MODE_CONT_COMP:
860                         if (!meye_emptyq(&meye.grabq, &reqnr)) {
861                                 int size;
862                                 size = mchip_comp_read_frame(
863                                         v,
864                                         meye.grab_fbuffer + gbufsize * reqnr,
865                                         gbufsize);
866                                 if (size == -1)
867                                         break;
868                                 reqnr = meye_pullq(&meye.grabq);
869                                 meye.grab_buffer[reqnr].size = size;
870                                 meye.grab_buffer[reqnr].state = MEYE_BUF_DONE;
871                                 wake_up_interruptible(&meye.grabq.proc_list);
872                         }
873                         break;
874
875                 default:
876                         /* do not free frame, since it can be a snap */
877                         return;
878                 } /* switch */
879
880                 mchip_free_frame();
881         }
882 }
883
884 /****************************************************************************/
885 /* video4linux integration                                                  */
886 /****************************************************************************/
887
888 static int meye_open(struct inode *inode, struct file *file) {
889         int i, err;
890
891         err = video_exclusive_open(inode,file);
892         if (err < 0)
893                 return err;
894                         
895         if (mchip_dma_alloc()) {
896                 printk(KERN_ERR "meye: mchip framebuffer allocation failed\n");
897                 video_exclusive_release(inode,file);
898                 return -ENOBUFS;
899         }
900         mchip_hic_stop();
901         meye_initq(&meye.grabq);
902         for (i = 0; i < MEYE_MAX_BUFNBRS; i++)
903                 meye.grab_buffer[i].state = MEYE_BUF_UNUSED;
904         return 0;
905 }
906
907 static int meye_release(struct inode *inode, struct file *file) {
908         mchip_hic_stop();
909         mchip_dma_free();
910         video_exclusive_release(inode,file);
911         return 0;
912 }
913
914 static int meye_do_ioctl(struct inode *inode, struct file *file,
915                          unsigned int cmd, void *arg) {
916
917         switch (cmd) {
918
919         case VIDIOCGCAP: {
920                 struct video_capability *b = arg;
921                 strcpy(b->name,meye.video_dev.name);
922                 b->type = VID_TYPE_CAPTURE;
923                 b->channels = 1;
924                 b->audios = 0;
925                 b->maxwidth = 640;
926                 b->maxheight = 480;
927                 b->minwidth = 320;
928                 b->minheight = 240;
929                 break;
930         }
931
932         case VIDIOCGCHAN: {
933                 struct video_channel *v = arg;
934                 v->flags = 0;
935                 v->tuners = 0;
936                 v->type = VIDEO_TYPE_CAMERA;
937                 if (v->channel != 0)
938                         return -EINVAL;
939                 strcpy(v->name,"Camera");
940                 break;
941         }
942
943         case VIDIOCSCHAN: {
944                 struct video_channel *v = arg;
945                 if (v->channel != 0)
946                         return -EINVAL;
947                 break;
948         }
949
950         case VIDIOCGPICT: {
951                 struct video_picture *p = arg;
952                 *p = meye.picture;
953                 break;
954         }
955
956         case VIDIOCSPICT: {
957                 struct video_picture *p = arg;
958                 if (p->depth != 2)
959                         return -EINVAL;
960                 if (p->palette != VIDEO_PALETTE_YUV422)
961                         return -EINVAL;
962                 down(&meye.lock);
963                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERABRIGHTNESS, 
964                                       p->brightness >> 10);
965                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERAHUE, 
966                                       p->hue >> 10);
967                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERACOLOR, 
968                                       p->colour >> 10);
969                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERACONTRAST, 
970                                       p->contrast >> 10);
971                 meye.picture = *p;
972                 up(&meye.lock);
973                 break;
974         }
975
976         case VIDIOCSYNC: {
977                 int *i = arg;
978
979                 if (*i < 0 || *i >= gbuffers)
980                         return -EINVAL;
981
982                 switch (meye.grab_buffer[*i].state) {
983
984                 case MEYE_BUF_UNUSED:
985                         return -EINVAL;
986                 case MEYE_BUF_USING:
987                         if (wait_event_interruptible(meye.grabq.proc_list,
988                                                      (meye.grab_buffer[*i].state != MEYE_BUF_USING)))
989                                 return -EINTR;
990                         /* fall through */
991                 case MEYE_BUF_DONE:
992                         meye.grab_buffer[*i].state = MEYE_BUF_UNUSED;
993                 }
994                 break;
995         }
996
997         case VIDIOCMCAPTURE: {
998                 struct video_mmap *vm = arg;
999                 int restart = 0;
1000
1001                 if (vm->frame >= gbuffers || vm->frame < 0)
1002                         return -EINVAL;
1003                 if (vm->format != VIDEO_PALETTE_YUV422)
1004                         return -EINVAL;
1005                 if (vm->height * vm->width * 2 > gbufsize)
1006                         return -EINVAL;
1007                 if (!meye.grab_fbuffer)
1008                         return -EINVAL;
1009                 if (meye.grab_buffer[vm->frame].state != MEYE_BUF_UNUSED)
1010                         return -EBUSY;
1011
1012                 down(&meye.lock);
1013                 if (vm->width == 640 && vm->height == 480) {
1014                         if (meye.params.subsample) {
1015                                 meye.params.subsample = 0;
1016                                 restart = 1;
1017                         }
1018                 }
1019                 else if (vm->width == 320 && vm->height == 240) {
1020                         if (!meye.params.subsample) {
1021                                 meye.params.subsample = 1;
1022                                 restart = 1;
1023                         }
1024                 }
1025                 else {
1026                         up(&meye.lock);
1027                         return -EINVAL;
1028                 }
1029
1030                 if (restart || meye.mchip_mode != MCHIP_HIC_MODE_CONT_OUT)
1031                         mchip_continuous_start();
1032                 meye.grab_buffer[vm->frame].state = MEYE_BUF_USING;
1033                 meye_pushq(&meye.grabq, vm->frame);
1034                 up(&meye.lock);
1035                 break;
1036         }
1037
1038         case VIDIOCGMBUF: {
1039                 struct video_mbuf *vm = arg;
1040                 int i;
1041
1042                 memset(vm, 0 , sizeof(*vm));
1043                 vm->size = gbufsize * gbuffers;
1044                 vm->frames = gbuffers;
1045                 for (i = 0; i < gbuffers; i++)
1046                         vm->offsets[i] = i * gbufsize;
1047                 break;
1048         }
1049
1050         case MEYEIOC_G_PARAMS: {
1051                 struct meye_params *p = arg;
1052                 *p = meye.params;
1053                 break;
1054         }
1055
1056         case MEYEIOC_S_PARAMS: {
1057                 struct meye_params *jp = arg;
1058                 if (jp->subsample > 1)
1059                         return -EINVAL;
1060                 if (jp->quality > 10)
1061                         return -EINVAL;
1062                 if (jp->sharpness > 63 || jp->agc > 63 || jp->picture > 63)
1063                         return -EINVAL;
1064                 if (jp->framerate > 31)
1065                         return -EINVAL;
1066                 down(&meye.lock);
1067                 if (meye.params.subsample != jp->subsample ||
1068                     meye.params.quality != jp->quality)
1069                         mchip_hic_stop();       /* need restart */
1070                 meye.params = *jp;
1071                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERASHARPNESS,
1072                                       meye.params.sharpness);
1073                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERAAGC,
1074                                       meye.params.agc);
1075                 sonypi_camera_command(SONYPI_COMMAND_SETCAMERAPICTURE,
1076                                       meye.params.picture);
1077                 up(&meye.lock);
1078                 break;
1079         }
1080
1081         case MEYEIOC_QBUF_CAPT: {
1082                 int *nb = arg;
1083
1084                 if (!meye.grab_fbuffer) 
1085                         return -EINVAL;
1086                 if (*nb >= gbuffers)
1087                         return -EINVAL;
1088                 if (*nb < 0) {
1089                         /* stop capture */
1090                         mchip_hic_stop();
1091                         return 0;
1092                 }
1093                 if (meye.grab_buffer[*nb].state != MEYE_BUF_UNUSED)
1094                         return -EBUSY;
1095                 down(&meye.lock);
1096                 if (meye.mchip_mode != MCHIP_HIC_MODE_CONT_COMP)
1097                         mchip_cont_compression_start();
1098                 meye.grab_buffer[*nb].state = MEYE_BUF_USING;
1099                 meye_pushq(&meye.grabq, *nb);
1100                 up(&meye.lock);
1101                 break;
1102         }
1103
1104         case MEYEIOC_SYNC: {
1105                 int *i = arg;
1106
1107                 if (*i < 0 || *i >= gbuffers)
1108                         return -EINVAL;
1109
1110                 switch (meye.grab_buffer[*i].state) {
1111
1112                 case MEYE_BUF_UNUSED:
1113                         return -EINVAL;
1114                 case MEYE_BUF_USING:
1115                         if (wait_event_interruptible(meye.grabq.proc_list,
1116                                                      (meye.grab_buffer[*i].state != MEYE_BUF_USING)))
1117                                 return -EINTR;
1118                         /* fall through */
1119                 case MEYE_BUF_DONE:
1120                         meye.grab_buffer[*i].state = MEYE_BUF_UNUSED;
1121                 }
1122                 *i = meye.grab_buffer[*i].size;
1123                 break;
1124         }
1125
1126         case MEYEIOC_STILLCAPT: {
1127
1128                 if (!meye.grab_fbuffer) 
1129                         return -EINVAL;
1130                 if (meye.grab_buffer[0].state != MEYE_BUF_UNUSED)
1131                         return -EBUSY;
1132                 down(&meye.lock);
1133                 meye.grab_buffer[0].state = MEYE_BUF_USING;
1134                 mchip_take_picture();
1135                 mchip_get_picture(
1136                         meye.grab_fbuffer,
1137                         mchip_hsize() * mchip_vsize() * 2);
1138                 meye.grab_buffer[0].state = MEYE_BUF_DONE;
1139                 up(&meye.lock);
1140                 break;
1141         }
1142
1143         case MEYEIOC_STILLJCAPT: {
1144                 int *len = arg;
1145
1146                 if (!meye.grab_fbuffer) 
1147                         return -EINVAL;
1148                 if (meye.grab_buffer[0].state != MEYE_BUF_UNUSED)
1149                         return -EBUSY;
1150                 down(&meye.lock);
1151                 meye.grab_buffer[0].state = MEYE_BUF_USING;
1152                 *len = -1;
1153                 while (*len == -1) {
1154                         mchip_take_picture();
1155                         *len = mchip_compress_frame(meye.grab_fbuffer, gbufsize);
1156                 }
1157                 meye.grab_buffer[0].state = MEYE_BUF_DONE;
1158                 up(&meye.lock);
1159                 break;
1160         }
1161
1162         default:
1163                 return -ENOIOCTLCMD;
1164                 
1165         } /* switch */
1166
1167         return 0;
1168 }
1169
1170 static int meye_ioctl(struct inode *inode, struct file *file,
1171                      unsigned int cmd, unsigned long arg)
1172 {
1173         return video_usercopy(inode, file, cmd, arg, meye_do_ioctl);
1174 }
1175
1176 static int meye_mmap(struct file *file, struct vm_area_struct *vma) {
1177         unsigned long start = vma->vm_start;
1178         unsigned long size  = vma->vm_end - vma->vm_start;
1179         unsigned long page, pos;
1180
1181         down(&meye.lock);
1182         if (size > gbuffers * gbufsize) {
1183                 up(&meye.lock);
1184                 return -EINVAL;
1185         }
1186         if (!meye.grab_fbuffer) {
1187                 /* lazy allocation */
1188                 meye.grab_fbuffer = rvmalloc(gbuffers*gbufsize);
1189                 if (!meye.grab_fbuffer) {
1190                         printk(KERN_ERR "meye: v4l framebuffer allocation failed\n");
1191                         up(&meye.lock);
1192                         return -ENOMEM;
1193                 }
1194         }
1195         pos = (unsigned long)meye.grab_fbuffer;
1196
1197         while (size > 0) {
1198                 page = kvirt_to_pa(pos);
1199                 if (remap_page_range(start, page, PAGE_SIZE, PAGE_SHARED)) {
1200                         up(&meye.lock);
1201                         return -EAGAIN;
1202                 }
1203                 start += PAGE_SIZE;
1204                 pos += PAGE_SIZE;
1205                 size -= PAGE_SIZE;
1206         }
1207         up(&meye.lock);
1208         return 0;
1209 }
1210
1211 static struct file_operations meye_fops = {
1212         .owner          = THIS_MODULE,
1213         .open           = meye_open,
1214         .release        = meye_release,
1215         .mmap           = meye_mmap,
1216         .ioctl          = meye_ioctl,
1217         .llseek         = no_llseek,
1218 };
1219
1220 static struct video_device meye_template = {
1221         .owner          = THIS_MODULE,
1222         .name           = "meye",
1223         .type           = VID_TYPE_CAPTURE,
1224         .hardware       = VID_HARDWARE_MEYE,
1225         .fops           = &meye_fops,
1226 };
1227
1228 static int __devinit meye_probe(struct pci_dev *pcidev, 
1229                                 const struct pci_device_id *ent) {
1230         int ret;
1231         unsigned long mchip_adr;
1232         u8 revision;
1233
1234         if (meye.mchip_dev != NULL) {
1235                 printk(KERN_ERR "meye: only one device allowed!\n");
1236                 ret = -EBUSY;
1237                 goto out1;
1238         }
1239
1240         sonypi_camera_command(SONYPI_COMMAND_SETCAMERA, 1);
1241
1242         meye.mchip_dev = pcidev;
1243         memcpy(&meye.video_dev, &meye_template, sizeof(meye_template));
1244
1245         if ((ret = pci_enable_device(meye.mchip_dev))) {
1246                 printk(KERN_ERR "meye: pci_enable_device failed\n");
1247                 goto out2;
1248         }
1249
1250         meye.mchip_irq = pcidev->irq;
1251         mchip_adr = pci_resource_start(meye.mchip_dev,0);
1252         if (!mchip_adr) {
1253                 printk(KERN_ERR "meye: mchip has no device base address\n");
1254                 ret = -EIO;
1255                 goto out3;
1256         }
1257         if (!request_mem_region(pci_resource_start(meye.mchip_dev, 0),
1258                                 pci_resource_len(meye.mchip_dev, 0),
1259                                 "meye")) {
1260                 ret = -EIO;
1261                 printk(KERN_ERR "meye: request_mem_region failed\n");
1262                 goto out3;
1263         }
1264
1265         pci_read_config_byte(meye.mchip_dev, PCI_REVISION_ID, &revision);
1266
1267         pci_set_master(meye.mchip_dev);
1268
1269         pci_write_config_byte(meye.mchip_dev, PCI_CACHE_LINE_SIZE, 8);
1270         pci_write_config_byte(meye.mchip_dev, PCI_LATENCY_TIMER, 64);
1271
1272         if ((ret = request_irq(meye.mchip_irq, meye_irq, 
1273                                SA_INTERRUPT | SA_SHIRQ, "meye", meye_irq))) {
1274                 printk(KERN_ERR "meye: request_irq failed (ret=%d)\n", ret);
1275                 goto out4;
1276         }
1277
1278         meye.mchip_mmregs = ioremap(mchip_adr, MCHIP_MM_REGS);
1279         if (!meye.mchip_mmregs) {
1280                 printk(KERN_ERR "meye: ioremap failed\n");
1281                 ret = -EIO;
1282                 goto out5;
1283         }
1284         
1285         /* Ask the camera to perform a soft reset. */
1286         pci_write_config_word(meye.mchip_dev, MCHIP_PCI_SOFTRESET_SET, 1);
1287
1288         mchip_delay(MCHIP_HIC_CMD, 0);
1289         mchip_delay(MCHIP_HIC_STATUS, MCHIP_HIC_STATUS_IDLE);
1290
1291         wait_ms(1);
1292         mchip_set(MCHIP_VRJ_SOFT_RESET, 1);
1293
1294         wait_ms(1);
1295         mchip_set(MCHIP_MM_PCI_MODE, 5);
1296
1297         wait_ms(1);
1298         mchip_set(MCHIP_MM_INTA, MCHIP_MM_INTA_HIC_1_MASK);
1299
1300         if (video_register_device(&meye.video_dev, VFL_TYPE_GRABBER, video_nr) < 0) {
1301
1302                 printk(KERN_ERR "meye: video_register_device failed\n");
1303                 ret = -EIO;
1304                 goto out6;
1305         }
1306         
1307         printk(KERN_INFO "meye: Motion Eye Camera Driver v%d.%d.\n",
1308                MEYE_DRIVER_MAJORVERSION,
1309                MEYE_DRIVER_MINORVERSION);
1310         printk(KERN_INFO "meye: mchip KL5A72002 rev. %d, base %lx, irq %d\n", 
1311                 revision, mchip_adr, meye.mchip_irq);
1312
1313         /* init all fields */
1314         init_MUTEX(&meye.lock);
1315
1316         meye.picture.depth = 2;
1317         meye.picture.palette = VIDEO_PALETTE_YUV422;
1318         meye.picture.brightness = 32 << 10;
1319         meye.picture.hue = 32 << 10;
1320         meye.picture.colour = 32 << 10;
1321         meye.picture.contrast = 32 << 10;
1322         meye.picture.whiteness = 0;
1323         meye.params.subsample = 0;
1324         meye.params.quality = 7;
1325         meye.params.sharpness = 32;
1326         meye.params.agc = 48;
1327         meye.params.picture = 0;
1328         meye.params.framerate = 0;
1329         sonypi_camera_command(SONYPI_COMMAND_SETCAMERABRIGHTNESS, 32);
1330         sonypi_camera_command(SONYPI_COMMAND_SETCAMERAHUE, 32);
1331         sonypi_camera_command(SONYPI_COMMAND_SETCAMERACOLOR, 32);
1332         sonypi_camera_command(SONYPI_COMMAND_SETCAMERACONTRAST, 32);
1333         sonypi_camera_command(SONYPI_COMMAND_SETCAMERASHARPNESS, 32);
1334         sonypi_camera_command(SONYPI_COMMAND_SETCAMERAPICTURE, 0);
1335         sonypi_camera_command(SONYPI_COMMAND_SETCAMERAAGC, 48);
1336
1337         return 0;
1338 out6:
1339         iounmap(meye.mchip_mmregs);
1340 out5:
1341         free_irq(meye.mchip_irq, meye_irq);
1342 out4:
1343         release_mem_region(pci_resource_start(meye.mchip_dev, 0),
1344                            pci_resource_len(meye.mchip_dev, 0));
1345 out3:
1346         pci_disable_device(meye.mchip_dev);
1347 out2:
1348         sonypi_camera_command(SONYPI_COMMAND_SETCAMERA, 0);
1349 out1:
1350         return ret;
1351 }
1352
1353 static void __devexit meye_remove(struct pci_dev *pcidev) {
1354
1355         video_unregister_device(&meye.video_dev);
1356
1357         mchip_hic_stop();
1358
1359         /* disable interrupts */
1360         mchip_set(MCHIP_MM_INTA, 0x0);
1361
1362         free_irq(meye.mchip_irq, meye_irq);
1363
1364         iounmap(meye.mchip_mmregs);
1365
1366         release_mem_region(pci_resource_start(meye.mchip_dev, 0),
1367                            pci_resource_len(meye.mchip_dev, 0));
1368
1369         pci_disable_device(meye.mchip_dev);
1370
1371         mchip_dma_free();
1372
1373         if (meye.grab_fbuffer)
1374                 rvfree(meye.grab_fbuffer, gbuffers*gbufsize);
1375
1376         sonypi_camera_command(SONYPI_COMMAND_SETCAMERA, 0);
1377
1378         printk(KERN_INFO "meye: removed\n");
1379 }
1380
1381 static struct pci_device_id meye_pci_tbl[] __devinitdata = {
1382         { PCI_VENDOR_ID_KAWASAKI, PCI_DEVICE_ID_MCHIP_KL5A72002, 
1383           PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
1384         { }
1385 };
1386
1387 MODULE_DEVICE_TABLE(pci, meye_pci_tbl);
1388
1389 static struct pci_driver meye_driver = {
1390         .name           = "meye",
1391         .id_table       = meye_pci_tbl,
1392         .probe          = meye_probe,
1393         .remove         = __devexit_p(meye_remove),
1394 };
1395
1396 static int __init meye_init_module(void) {
1397         if (gbuffers < 2)
1398                 gbuffers = 2;
1399         if (gbuffers > MEYE_MAX_BUFNBRS)
1400                 gbuffers = MEYE_MAX_BUFNBRS;
1401         if (gbufsize < 0 || gbufsize > MEYE_MAX_BUFSIZE)
1402                 gbufsize = MEYE_MAX_BUFSIZE;
1403         printk(KERN_INFO "meye: using %d buffers with %dk (%dk total) for capture\n",
1404                gbuffers, gbufsize/1024, gbuffers*gbufsize/1024);
1405         return pci_module_init(&meye_driver);
1406 }
1407
1408 static void __exit meye_cleanup_module(void) {
1409         pci_unregister_driver(&meye_driver);
1410 }
1411
1412 #ifndef MODULE
1413 static int __init meye_setup(char *str) {
1414         int ints[4];
1415
1416         str = get_options(str, ARRAY_SIZE(ints), ints);
1417         if (ints[0] <= 0) 
1418                 goto out;
1419         gbuffers = ints[1];
1420         if (ints[0] == 1)
1421                 goto out;
1422         gbufsize = ints[2];
1423         if (ints[0] == 2)
1424                 goto out;
1425         video_nr = ints[3];
1426 out:
1427         return 1;
1428 }
1429
1430 __setup("meye=", meye_setup);
1431 #endif
1432
1433 MODULE_AUTHOR("Stelian Pop <stelian@popies.net>");
1434 MODULE_DESCRIPTION("video4linux driver for the MotionEye camera");
1435 MODULE_LICENSE("GPL");
1436
1437 EXPORT_NO_SYMBOLS;
1438
1439 MODULE_PARM(gbuffers,"i");
1440 MODULE_PARM_DESC(gbuffers,"number of capture buffers, default is 2 (32 max)");
1441 MODULE_PARM(gbufsize,"i");
1442 MODULE_PARM_DESC(gbufsize,"size of the capture buffers, default is 614400");
1443 MODULE_PARM(video_nr,"i");
1444 MODULE_PARM_DESC(video_nr,"video device to register (0=/dev/video0, etc)");
1445
1446 /* Module entry points */
1447 module_init(meye_init_module);
1448 module_exit(meye_cleanup_module);