Subversion Repositories shark

Rev

Rev 516 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
516 giacomo 1
/*
2
 * generic helper functions for video4linux capture buffers, to handle
3
 * memory management and PCI DMA.  Right now bttv + saa7134 use it.
4
 *
5
 * The functions expect the hardware being able to scatter gatter
6
 * (i.e. the buffers are not linear in physical memory, but fragmented
7
 * into PAGE_SIZE chunks).  They also assume the driver does not need
8
 * to touch the video data (thus it is probably not useful for USB as
9
 * data often must be uncompressed by the drivers).
10
 *
11
 * (c) 2001,02 Gerd Knorr <kraxel@bytesex.org>
12
 *
13
 * This program is free software; you can redistribute it and/or modify
14
 * it under the terms of the GNU General Public License as published by
15
 * the Free Software Foundation; either version 2 of the License, or
16
 * (at your option) any later version.
17
 */
18
 
19
#include <linuxcomp.h>
20
 
21
#include <linux/init.h>
22
#include <linux/module.h>
23
#include <linux/vmalloc.h>
24
#include <linux/pagemap.h>
25
#include <linux/slab.h>
26
#include <linux/pci.h>
27
#include <linux/interrupt.h>
28
#include <asm/page.h>
29
#include <asm/pgtable.h>
30
 
31
#ifndef TryLockPage
32
# include "linux/page-flags.h"
33
# define TryLockPage TestSetPageLocked
34
#endif
35
 
36
#include <media/video-buf.h>
37
 
38
static int debug = 1;
39
 
40
MODULE_DESCRIPTION("helper module to manage video4linux pci dma buffers");
41
MODULE_AUTHOR("Gerd Knorr <kraxel@bytesex.org> [SuSE Labs]");
42
MODULE_LICENSE("GPL");
43
MODULE_PARM(debug,"i");
44
 
45
#define dprintk(level, fmt, arg...)     if (debug >= level) \
46
        printk(KERN_DEBUG "vbuf: " fmt, ## arg)
47
 
48
/*
49
struct scatterlist*
50
videobuf_vmalloc_to_sg(unsigned char *virt, int nr_pages)
51
{
52
        struct scatterlist *sglist;
53
        struct page *pg;
54
        int i;
55
 
56
        sglist = kmalloc(sizeof(struct scatterlist)*nr_pages, GFP_KERNEL);
57
        if (NULL == sglist)
58
                return NULL;
59
        memset(sglist,0,sizeof(struct scatterlist)*nr_pages);
60
        for (i = 0; i < nr_pages; i++, virt += PAGE_SIZE) {
61
                pg = vmalloc_to_page(virt);
62
                if (NULL == pg)
63
                        goto err;
64
                if (PageHighMem(pg))
65
                        BUG();
66
                sglist[i].page   = pg;
67
                sglist[i].length = PAGE_SIZE;
68
        }
69
        return sglist;
70
 
71
 err:
72
        kfree(sglist);
73
        return NULL;
74
}
75
 
76
struct scatterlist*
77
videobuf_pages_to_sg(struct page **pages, int nr_pages, int offset)
78
{
79
        struct scatterlist *sglist;
80
        int i = 0;
81
 
82
        if (NULL == pages[0])
83
                return NULL;
84
        sglist = kmalloc(sizeof(*sglist) * nr_pages, GFP_KERNEL);
85
        if (NULL == sglist)
86
                return NULL;
87
        memset(sglist, 0, sizeof(*sglist) * nr_pages);
88
 
89
        if (NULL == pages[0])
90
                goto nopage;
91
        if (PageHighMem(pages[0]))
92
                goto highmem;
93
        sglist[0].page   = pages[0];
94
        sglist[0].offset = offset;
95
        sglist[0].length = PAGE_SIZE - offset;
96
        for (i = 1; i < nr_pages; i++) {
97
                if (NULL == pages[i])
98
                        goto nopage;
99
                if (PageHighMem(pages[i]))
100
                        goto highmem;
101
                sglist[i].page   = pages[i];
102
                sglist[i].length = PAGE_SIZE;
103
        }
104
        return sglist;
105
 
106
 nopage:
107
        dprintk(2,"sgl: oops - no page\n");
108
        kfree(sglist);
109
        return NULL;
110
 
111
 highmem:
112
        dprintk(2,"sgl: oops - highmem page\n");
113
        kfree(sglist);
114
        return NULL;
115
}
116
*/
117
int videobuf_lock(struct page **pages, int nr_pages)
118
{
119
        int i = 0;
120
 
121
        dprintk(2,"lock start ...\n");
122
        //for (i = 0; i < nr_pages; i++)
123
        //      if (TryLockPage(pages[i]))
124
        //              goto err;
125
        dprintk(2,"lock ok [%d pages]\n",nr_pages);
126
        return 0;
127
 
128
// err:
129
        dprintk(2,"lock failed, unlock ...\n");
130
        while (i > 0)
131
                //unlock_page(pages[--i]);
132
        dprintk(2,"lock quit\n");
133
        return -EINVAL;
134
}
135
 
136
int videobuf_unlock(struct page **pages, int nr_pages)
137
{
138
        //int i;
139
 
140
        dprintk(2,"unlock start ...\n");
141
        //for (i = 0; i < nr_pages; i++)
142
        //      unlock_page(pages[i]);
143
        dprintk(2,"unlock ok [%d pages]\n",nr_pages);
144
        return 0;
145
}
146
 
147
/* --------------------------------------------------------------------- */
148
 
149
int videobuf_dma_init_user(struct videobuf_dmabuf *dma, int direction,
150
                           unsigned long data, unsigned long size)
151
{
152
        unsigned long first,last;
153
        int err, rw = 0;
154
 
155
        dma->direction = direction;
156
        switch (dma->direction) {
157
        case PCI_DMA_FROMDEVICE: rw = READ;  break;
158
        case PCI_DMA_TODEVICE:   rw = WRITE; break;
159
        default:                 BUG();
160
        }
161
 
162
        first = (data          & PAGE_MASK) >> PAGE_SHIFT;
163
        last  = ((data+size-1) & PAGE_MASK) >> PAGE_SHIFT;
164
        dma->offset   = data & ~PAGE_MASK;
165
        dma->nr_pages = last-first+1;
166
        dma->pages = kmalloc(dma->nr_pages * sizeof(struct page*),
167
                             GFP_KERNEL);
168
        if (NULL == dma->pages)
169
                return -ENOMEM;
170
        dprintk(1,"init user [0x%lx+0x%lx => %d pages]\n",
171
                data,size,dma->nr_pages);
172
 
173
        //down_read(&current->mm->mmap_sem);
174
        err = dma->nr_pages;//get_user_pages(current,current->mm,
175
                //           data & PAGE_MASK, dma->nr_pages,
176
                //           rw == READ, 1, /* force */
177
                //           dma->pages, NULL);
178
        //up_read(&current->mm->mmap_sem);
179
        if (err != dma->nr_pages) {
180
                dma->nr_pages = (err >= 0) ? err : 0;
181
                dprintk(1,"get_user_pages: err=%d [%d]\n",err,dma->nr_pages);
182
                return err < 0 ? err : -EINVAL;
183
        }
184
        return 0;
185
}
186
 
187
int videobuf_dma_init_kernel(struct videobuf_dmabuf *dma, int direction,
188
                             int nr_pages)
189
{
190
        dprintk(1,"init kernel [%d pages]\n",nr_pages);
191
        dma->direction = direction;
192
        dma->vmalloc = vmalloc_32(nr_pages << PAGE_SHIFT);
193
        if (NULL == dma->vmalloc) {
194
                dprintk(1,"vmalloc_32(%d pages) failed\n",nr_pages);
195
                return -ENOMEM;
196
        }
197
        memset(dma->vmalloc,0,nr_pages << PAGE_SHIFT);
198
        dma->nr_pages = nr_pages;
199
        return 0;
200
}
201
 
202
int videobuf_dma_init_overlay(struct videobuf_dmabuf *dma, int direction,
203
                              dma_addr_t addr, int nr_pages)
204
{
205
        dprintk(1,"init overlay [%d pages @ bus 0x%lx]\n",
206
                nr_pages,(unsigned long)addr);
207
        dma->direction = direction;
208
        if (0 == addr)
209
                return -EINVAL;
210
 
211
        dma->bus_addr = addr;
212
        dma->nr_pages = nr_pages;
213
        return 0;
214
}
215
/*
216
int videobuf_dma_pci_map(struct pci_dev *dev, struct videobuf_dmabuf *dma)
217
{
218
        int err;
219
 
220
        if (0 == dma->nr_pages)
221
                BUG();
222
 
223
        if (dma->pages) {
224
                if (0 != (err = videobuf_lock(dma->pages, dma->nr_pages))) {
225
                        dprintk(1,"videobuf_lock: %d\n",err);
226
                        return err;
227
                }
228
                dma->sglist = videobuf_pages_to_sg(dma->pages, dma->nr_pages,
229
                                                   dma->offset);
230
                if (NULL == dma->sglist)
231
                        videobuf_unlock(dma->pages, dma->nr_pages);
232
        }
233
        if (dma->vmalloc) {
234
                dma->sglist = videobuf_vmalloc_to_sg
235
                        (dma->vmalloc,dma->nr_pages);
236
        }
237
        if (dma->bus_addr) {
238
                dma->sglist = kmalloc(sizeof(struct scatterlist), GFP_KERNEL);
239
                if (NULL != dma->sglist) {
240
                        dma->sglen  = 1;
241
                        sg_dma_address(&dma->sglist[0]) = dma->bus_addr & ~PAGE_MASK;
242
                        dma->sglist[0].offset           = dma->bus_addr & PAGE_MASK;
243
                        sg_dma_len(&dma->sglist[0])     = dma->nr_pages * PAGE_SIZE;
244
                }
245
        }
246
        if (NULL == dma->sglist) {
247
                dprintk(1,"scatterlist is NULL\n");
248
                return -ENOMEM;
249
        }
250
 
251
        if (!dma->bus_addr)
252
                dma->sglen = pci_map_sg(dev,dma->sglist,dma->nr_pages,
253
                                        dma->direction);
254
        return 0;
255
}
256
 
257
int videobuf_dma_pci_sync(struct pci_dev *dev, struct videobuf_dmabuf *dma)
258
{
259
        if (!dma->sglen)
260
                BUG();
261
 
262
        if (!dma->bus_addr)
263
                pci_dma_sync_sg(dev,dma->sglist,dma->nr_pages,dma->direction);
264
        return 0;
265
}
266
 
267
int videobuf_dma_pci_unmap(struct pci_dev *dev, struct videobuf_dmabuf *dma)
268
{
269
        if (!dma->sglen)
270
                return 0;
271
 
272
        if (!dma->bus_addr)
273
                pci_unmap_sg(dev,dma->sglist,dma->nr_pages,dma->direction);
274
        kfree(dma->sglist);
275
        dma->sglist = NULL;
276
        dma->sglen = 0;
277
        if (dma->pages)
278
                videobuf_unlock(dma->pages, dma->nr_pages);
279
        return 0;
280
}
281
 
282
int videobuf_dma_free(struct videobuf_dmabuf *dma)
283
{
284
        if (dma->sglen)
285
                BUG();
286
 
287
        if (dma->pages) {
288
                int i;
289
                for (i=0; i < dma->nr_pages; i++)
290
                        page_cache_release(dma->pages[i]);
291
                kfree(dma->pages);
292
                dma->pages = NULL;
293
        }
294
        if (dma->vmalloc) {
295
                vfree(dma->vmalloc);
296
                dma->vmalloc = NULL;
297
        }
298
        if (dma->bus_addr) {
299
                dma->bus_addr = 0;
300
        }
301
        dma->direction = PCI_DMA_NONE;
302
        return 0;
303
}
304
*/
305
/* --------------------------------------------------------------------- */
306
 
307
void* videobuf_alloc(unsigned int size)
308
{
309
        struct videobuf_buffer *vb;
310
 
311
        vb = kmalloc(size,GFP_KERNEL);
312
        if (NULL != vb) {
313
                memset(vb,0,size);
314
                //init_waitqueue_head(&vb->done);
315
        }
316
        return vb;
317
}
318
 
319
int videobuf_waiton(struct videobuf_buffer *vb, int non_blocking, int intr)
320
{
321
        int retval = 0;
322
        /*
323
        DECLARE_WAITQUEUE(wait, current);
324
 
325
        add_wait_queue(&vb->done, &wait);
326
        while (vb->state == STATE_ACTIVE || vb->state == STATE_QUEUED) {
327
                if (non_blocking) {
328
                        retval = -EAGAIN;
329
                        break;
330
                }
331
                set_current_state(intr ? TASK_INTERRUPTIBLE :
332
                                        TASK_UNINTERRUPTIBLE);
333
                if (vb->state == STATE_ACTIVE || vb->state == STATE_QUEUED)
334
                        schedule();
335
                set_current_state(TASK_RUNNING);
336
                if (intr && signal_pending(current)) {
337
                        dprintk(1,"buffer waiton: -EINTR\n");
338
                        retval = -EINTR;
339
                        break;
340
                }
341
        }
342
        remove_wait_queue(&vb->done, &wait);
343
        */
344
        return retval;
345
}
346
 
347
int
348
videobuf_iolock(struct pci_dev *pci, struct videobuf_buffer *vb,
349
                struct v4l2_framebuffer *fbuf)
350
{
351
        int err,pages;
352
        dma_addr_t bus;
353
 
354
        switch (vb->memory) {
355
        case V4L2_MEMORY_MMAP:
356
        case V4L2_MEMORY_USERPTR:
357
                if (0 == vb->baddr) {
358
                        /* no userspace addr -- kernel bounce buffer */
359
                        pages = PAGE_ALIGN(vb->size) >> PAGE_SHIFT;
360
                        err = 0;//videobuf_dma_init_kernel(&vb->dma,PCI_DMA_FROMDEVICE,
361
                                //                     pages);
362
                        if (0 != err)
363
                                return err;
364
                } else {
365
                        /* dma directly to userspace */
366
                        err = 0;//videobuf_dma_init_user(&vb->dma,PCI_DMA_FROMDEVICE,
367
                                //                   vb->baddr,vb->bsize);
368
                        if (0 != err)
369
                                return err;
370
                }
371
                break;
372
        case V4L2_MEMORY_OVERLAY:
373
                if (NULL == fbuf)
374
                        return -EINVAL;
375
                /* FIXME: need sanity checks for vb->boff */
376
                bus   = (dma_addr_t)fbuf->base + vb->boff;
377
                pages = PAGE_ALIGN(vb->size) >> PAGE_SHIFT;
378
                err = 0;//videobuf_dma_init_overlay(&vb->dma,PCI_DMA_FROMDEVICE,
379
                        //                      bus, pages);
380
                if (0 != err)
381
                        return err;
382
                break;
383
        default:
384
                BUG();
385
        }
386
        err = 0;//videobuf_dma_pci_map(pci,&vb->dma);
387
        if (0 != err)
388
                return err;
389
 
390
        return 0;
391
}
392
 
393
/* --------------------------------------------------------------------- */
394
 
395
void
396
videobuf_queue_init(struct videobuf_queue *q,
397
                    struct videobuf_queue_ops *ops,
398
                    struct pci_dev *pci,
399
                    spinlock_t *irqlock,
400
                    enum v4l2_buf_type type,
401
                    enum v4l2_field field,
402
                    unsigned int msize)
403
{
404
        memset(q,0,sizeof(*q));
405
 
406
        q->irqlock = irqlock;
407
        q->pci     = pci;
408
        q->type    = type;
409
        q->field   = field;
410
        q->msize   = msize;
411
        q->ops     = ops;
412
 
413
        //init_MUTEX(&q->lock);
414
        INIT_LIST_HEAD(&q->stream);
415
}
416
 
417
int
418
videobuf_queue_is_busy(struct videobuf_queue *q)
419
{
420
        int i;
421
 
422
        if (q->streaming) {
423
                dprintk(1,"busy: streaming active\n");
424
                return 1;
425
        }
426
        if (q->reading) {
427
                dprintk(1,"busy: pending read #1\n");
428
                return 1;
429
        }
430
        if (q->read_buf) {
431
                dprintk(1,"busy: pending read #2\n");
432
                return 1;
433
        }
434
        for (i = 0; i < VIDEO_MAX_FRAME; i++) {
435
                if (NULL == q->bufs[i])
436
                        continue;
437
                if (q->bufs[i]->map) {
438
                        dprintk(1,"busy: buffer #%d mapped\n",i);
439
                        return 1;
440
                }
441
                if (q->bufs[i]->state == STATE_QUEUED) {
442
                        dprintk(1,"busy: buffer #%d queued\n",i);
443
                        return 1;
444
                }
445
                if (q->bufs[i]->state == STATE_ACTIVE) {
446
                        dprintk(1,"busy: buffer #%d avtive\n",i);
447
                        return 1;
448
                }
449
        }
450
        return 0;
451
}
452
 
453
void
454
videobuf_queue_cancel(struct file *file, struct videobuf_queue *q)
455
{
456
        unsigned long flags;
457
        int i;
458
 
459
        /* remove queued buffers from list */
460
        spin_lock_irqsave(q->irqlock,flags);
461
        for (i = 0; i < VIDEO_MAX_FRAME; i++) {
462
                if (NULL == q->bufs[i])
463
                        continue;
464
                if (q->bufs[i]->state == STATE_QUEUED) {
465
                        list_del(&q->bufs[i]->queue);
466
                        q->bufs[i]->state = STATE_ERROR;
467
                }
468
        }
469
        spin_unlock_irqrestore(q->irqlock,flags);
470
 
471
        /* free all buffers + clear queue */
472
        for (i = 0; i < VIDEO_MAX_FRAME; i++) {
473
                if (NULL == q->bufs[i])
474
                        continue;
475
                q->ops->buf_release(file,q->bufs[i]);
476
        }
477
        INIT_LIST_HEAD(&q->stream);
478
}
479
 
480
/* --------------------------------------------------------------------- */
481
 
482
enum v4l2_field
483
videobuf_next_field(struct videobuf_queue *q)
484
{
485
        enum v4l2_field field = q->field;
486
 
487
        BUG_ON(V4L2_FIELD_ANY == field);
488
 
489
        if (V4L2_FIELD_ALTERNATE == field) {
490
                if (V4L2_FIELD_TOP == q->last) {
491
                        field   = V4L2_FIELD_BOTTOM;
492
                        q->last = V4L2_FIELD_BOTTOM;
493
                } else {
494
                        field   = V4L2_FIELD_TOP;
495
                        q->last = V4L2_FIELD_TOP;
496
                }
497
        }
498
        return field;
499
}
500
 
501
void
502
videobuf_status(struct v4l2_buffer *b, struct videobuf_buffer *vb,
503
                enum v4l2_buf_type type)
504
{
505
        b->index    = vb->i;
506
        b->type     = type;
507
 
508
        b->memory   = vb->memory;
509
        switch (b->memory) {
510
        case V4L2_MEMORY_MMAP:
511
                b->m.offset  = vb->boff;
512
                b->length    = vb->bsize;
513
                break;
514
        case V4L2_MEMORY_USERPTR:
515
                b->m.userptr = vb->baddr;
516
                b->length    = vb->bsize;
517
                break;
518
        case V4L2_MEMORY_OVERLAY:
519
                b->m.offset  = vb->boff;
520
                break;
521
        }
522
 
523
        b->flags    = 0;
524
        if (vb->map)
525
                b->flags |= V4L2_BUF_FLAG_MAPPED;
526
 
527
        switch (vb->state) {
528
        case STATE_PREPARED:
529
        case STATE_QUEUED:
530
        case STATE_ACTIVE:
531
                b->flags |= V4L2_BUF_FLAG_QUEUED;
532
                break;
533
        case STATE_DONE:
534
        case STATE_ERROR:
535
                b->flags |= V4L2_BUF_FLAG_DONE;
536
                break;
537
        case STATE_NEEDS_INIT:
538
        case STATE_IDLE:
539
                /* nothing */
540
                break;
541
        }
542
 
543
        b->field     = vb->field;
544
        b->timestamp = vb->ts;
545
        b->bytesused = vb->size;
546
        b->sequence  = vb->field_count >> 1;
547
}
548
 
549
int
550
videobuf_reqbufs(struct file *file, struct videobuf_queue *q,
551
                 struct v4l2_requestbuffers *req)
552
{
553
        unsigned int size,count;
554
        int retval;
555
 
556
        if (req->type != q->type)
557
                return -EINVAL;
558
        if (req->count < 1)
559
                return -EINVAL;
560
        if (req->memory != V4L2_MEMORY_MMAP     &&
561
            req->memory != V4L2_MEMORY_USERPTR  &&
562
            req->memory != V4L2_MEMORY_OVERLAY)
563
                return -EINVAL;
564
 
565
        //down(&q->lock);
566
        count = req->count;
567
        if (count > VIDEO_MAX_FRAME)
568
                count = VIDEO_MAX_FRAME;
569
        size = 0;
570
        q->ops->buf_setup(file,&count,&size);
571
        size = PAGE_ALIGN(size);
572
        dprintk(1,"reqbufs: bufs=%d, size=0x%x [%d pages total]\n",
573
                count, size, (count*size)>>PAGE_SHIFT);
574
 
575
        retval = videobuf_mmap_setup(file,q,count,size,req->memory);
576
        if (retval < 0)
577
                goto done;
578
 
579
        req->count = count;
580
 
581
 done:
582
        //up(&q->lock);
583
        return retval;
584
}
585
 
586
int
587
videobuf_querybuf(struct videobuf_queue *q, struct v4l2_buffer *b)
588
{
589
        if (unlikely(b->type != q->type))
590
                return -EINVAL;
591
        if (unlikely(b->index < 0 || b->index >= VIDEO_MAX_FRAME))
592
                return -EINVAL;
593
        if (unlikely(NULL == q->bufs[b->index]))
594
                return -EINVAL;
595
        videobuf_status(b,q->bufs[b->index],q->type);
596
        return 0;
597
}
598
 
599
int
600
videobuf_qbuf(struct file *file, struct videobuf_queue *q,
601
              struct v4l2_buffer *b)
602
{
603
        struct videobuf_buffer *buf;
604
        enum v4l2_field field;
605
        unsigned long flags;
606
        int retval;
607
 
608
        //down(&q->lock);
609
        retval = -EBUSY;
610
        if (q->reading)
611
                goto done;
612
        retval = -EINVAL;
613
        if (b->type != q->type)
614
                goto done;
615
        if (b->index < 0 || b->index >= VIDEO_MAX_FRAME)
616
                goto done;
617
        buf = q->bufs[b->index];
618
        if (NULL == buf)
619
                goto done;
620
        if (buf->memory != b->memory)
621
                goto done;
622
        if (buf->state == STATE_QUEUED ||
623
            buf->state == STATE_ACTIVE)
624
                goto done;
625
 
626
        switch (b->memory) {
627
        case V4L2_MEMORY_MMAP:
628
                if (0 == buf->baddr)
629
                        goto done;
630
                break;
631
        case V4L2_MEMORY_USERPTR:
632
                if (b->length < buf->bsize)
633
                        goto done;
634
                buf->baddr = b->m.userptr;
635
                break;
636
        case V4L2_MEMORY_OVERLAY:
637
                buf->boff = b->m.offset;
638
                break;
639
        default:
640
                goto done;
641
        }
642
 
643
        field = videobuf_next_field(q);
644
        retval = q->ops->buf_prepare(file,buf,field);
645
        if (0 != retval)
646
                goto done;
647
 
648
        list_add_tail(&buf->stream,&q->stream);
649
        if (q->streaming) {
650
                spin_lock_irqsave(q->irqlock,flags);
651
                q->ops->buf_queue(file,buf);
652
                spin_unlock_irqrestore(q->irqlock,flags);
653
        }
654
        retval = 0;
655
 
656
 done:
657
        //up(&q->lock);
658
        return retval;
659
}
660
 
661
int
662
videobuf_dqbuf(struct file *file, struct videobuf_queue *q,
663
               struct v4l2_buffer *b)
664
{
665
        struct videobuf_buffer *buf;
666
        int retval;
667
 
668
        //down(&q->lock);
669
        retval = -EBUSY;
670
        if (q->reading)
671
                goto done;
672
        retval = -EINVAL;
673
        if (b->type != q->type)
674
                goto done;
675
        if (list_empty(&q->stream))
676
                goto done;
677
        buf = list_entry(q->stream.next, struct videobuf_buffer, stream);
678
        retval = videobuf_waiton(buf, file->f_flags & O_NONBLOCK, 1);
679
        if (retval < 0)
680
                goto done;
681
        switch (buf->state) {
682
        case STATE_ERROR:
683
                retval = -EIO;
684
                /* fall through */
685
        case STATE_DONE:
686
                //videobuf_dma_pci_sync(q->pci,&buf->dma);
687
                buf->state = STATE_IDLE;
688
                break;
689
        default:
690
                retval = -EINVAL;
691
                goto done;
692
        }
693
        list_del(&buf->stream);
694
        memset(b,0,sizeof(*b));
695
        videobuf_status(b,buf,q->type);
696
 
697
 done:
698
        //up(&q->lock);
699
        return retval;
700
}
701
 
702
int videobuf_streamon(struct file *file, struct videobuf_queue *q)
703
{
704
        struct videobuf_buffer *buf;
705
        struct list_head *list;
706
        unsigned long flags;
707
        int retval;
708
 
709
        //down(&q->lock);
710
        retval = -EBUSY;
711
        if (q->reading)
712
                goto done;
713
        retval = 0;
714
        if (q->streaming)
715
                goto done;
716
        q->streaming = 1;
717
        spin_lock_irqsave(q->irqlock,flags);
718
        list_for_each(list,&q->stream) {
719
                buf = list_entry(list, struct videobuf_buffer, stream);
720
                if (buf->state == STATE_PREPARED)
721
                        q->ops->buf_queue(file,buf);
722
        }
723
        spin_unlock_irqrestore(q->irqlock,flags);
724
 
725
 done:
726
        //up(&q->lock);
727
        return retval;
728
}
729
 
730
int videobuf_streamoff(struct file *file, struct videobuf_queue *q)
731
{
732
        int retval = -EINVAL;
733
 
734
        //down(&q->lock);
735
        if (!q->streaming)
736
                goto done;
737
        videobuf_queue_cancel(file,q);
738
        q->streaming = 0;
739
        retval = 0;
740
 
741
 done:
742
        //up(&q->lock);
743
        return retval;
744
}
745
 
746
static ssize_t
747
videobuf_read_zerocopy(struct file *file, struct videobuf_queue *q,
748
                       char *data, size_t count, loff_t *ppos)
749
{
750
        enum v4l2_field field;
751
        unsigned long flags;
752
        int retval;
753
 
754
        /* setup stuff */
755
        retval = -ENOMEM;
756
        q->read_buf = videobuf_alloc(q->msize);
757
        if (NULL == q->read_buf)
758
                goto done;
759
 
760
        q->read_buf->memory = V4L2_MEMORY_USERPTR;
761
        q->read_buf->baddr  = (unsigned long)data;
762
        q->read_buf->bsize  = count;
763
        field = videobuf_next_field(q);
764
        retval = q->ops->buf_prepare(file,q->read_buf,field);
765
        if (0 != retval)
766
                goto done;
767
 
768
        /* start capture & wait */
769
        spin_lock_irqsave(q->irqlock,flags);
770
        q->ops->buf_queue(file,q->read_buf);
771
        spin_unlock_irqrestore(q->irqlock,flags);
772
        retval = videobuf_waiton(q->read_buf,0,0);
773
        if (0 == retval) {
774
                //videobuf_dma_pci_sync(q->pci,&q->read_buf->dma);
775
                if (STATE_ERROR == q->read_buf->state)
776
                        retval = -EIO;
777
                else
778
                        retval = q->read_buf->size;
779
        }
780
 
781
 done:
782
        /* cleanup */
783
        q->ops->buf_release(file,q->read_buf);
784
        kfree(q->read_buf);
785
        q->read_buf = NULL;
786
        return retval;
787
}
788
 
789
ssize_t videobuf_read_one(struct file *file, struct videobuf_queue *q,
790
                          char *data, size_t count, loff_t *ppos)
791
{
792
        enum v4l2_field field;
793
        unsigned long flags;
794
        unsigned size, nbufs, bytes;
795
        int retval;
796
 
797
        //down(&q->lock);
798
 
799
        nbufs = 1; size = 0;
800
        q->ops->buf_setup(file,&nbufs,&size);
801
        if (NULL == q->read_buf  &&
802
            count >= size        &&
803
            !(file->f_flags & O_NONBLOCK)) {
804
                retval = videobuf_read_zerocopy(file,q,data,count,ppos);
805
                if (retval >= 0  ||  retval == -EIO)
806
                        /* ok, all done */
807
                        goto done;
808
                /* fallback to kernel bounce buffer on failures */
809
        }
810
 
811
        if (NULL == q->read_buf) {
812
                /* need to capture a new frame */
813
                retval = -ENOMEM;
814
                q->read_buf = videobuf_alloc(q->msize);
815
                if (NULL == q->read_buf)
816
                        goto done;
817
                q->read_buf->memory = V4L2_MEMORY_USERPTR;
818
                field = videobuf_next_field(q);
819
                retval = q->ops->buf_prepare(file,q->read_buf,field);
820
                if (0 != retval)
821
                        goto done;
822
                spin_lock_irqsave(q->irqlock,flags);
823
                q->ops->buf_queue(file,q->read_buf);
824
                spin_unlock_irqrestore(q->irqlock,flags);
825
                q->read_off = 0;
826
        }
827
 
828
        /* wait until capture is done */
829
        retval = videobuf_waiton(q->read_buf, file->f_flags & O_NONBLOCK, 1);
830
        if (0 != retval)
831
                goto done;
832
        //videobuf_dma_pci_sync(q->pci,&q->read_buf->dma);
833
 
834
        if (STATE_ERROR == q->read_buf->state) {
835
                /* catch I/O errors */
836
                q->ops->buf_release(file,q->read_buf);
837
                kfree(q->read_buf);
838
                q->read_buf = NULL;
839
                retval = -EIO;
840
                goto done;
841
        }
842
 
843
        /* copy to userspace */
844
        bytes = count;
845
        if (bytes > q->read_buf->size - q->read_off)
846
                bytes = q->read_buf->size - q->read_off;
847
        retval = -EFAULT;
848
        if (copy_to_user(data, q->read_buf->dma.vmalloc+q->read_off, bytes))
849
                goto done;
850
 
851
        retval = bytes;
852
        q->read_off += bytes;
853
        if (q->read_off == q->read_buf->size) {
854
                /* all data copied, cleanup */
855
                q->ops->buf_release(file,q->read_buf);
856
                kfree(q->read_buf);
857
                q->read_buf = NULL;
858
        }
859
 
860
 done:
861
        //up(&q->lock);
862
        return retval;
863
}
864
 
865
int videobuf_read_start(struct file *file, struct videobuf_queue *q)
866
{
867
        enum v4l2_field field;
868
        unsigned long flags;
869
        int count = 0, size = 0;
870
        int err, i;
871
 
872
        q->ops->buf_setup(file,&count,&size);
873
        if (count < 2)
874
                count = 2;
875
        if (count > VIDEO_MAX_FRAME)
876
                count = VIDEO_MAX_FRAME;
877
        size = PAGE_ALIGN(size);
878
 
879
        err = videobuf_mmap_setup(file, q, count, size, V4L2_MEMORY_USERPTR);
880
        if (err)
881
                return err;
882
        for (i = 0; i < count; i++) {
883
                field = videobuf_next_field(q);
884
                err = q->ops->buf_prepare(file,q->bufs[i],field);
885
                if (err)
886
                        return err;
887
                list_add_tail(&q->bufs[i]->stream, &q->stream);
888
        }
889
        spin_lock_irqsave(q->irqlock,flags);
890
        for (i = 0; i < count; i++)
891
                q->ops->buf_queue(file,q->bufs[i]);
892
        spin_unlock_irqrestore(q->irqlock,flags);
893
        q->reading = 1;
894
        return 0;
895
}
896
 
897
void videobuf_read_stop(struct file *file, struct videobuf_queue *q)
898
{
899
        int i;
900
 
901
        videobuf_queue_cancel(file,q);
902
        INIT_LIST_HEAD(&q->stream);
903
        for (i = 0; i < VIDEO_MAX_FRAME; i++) {
904
                if (NULL == q->bufs[i])
905
                        continue;
906
                kfree(q->bufs[i]);
907
                q->bufs[i] = NULL;
908
        }
909
        q->read_buf = NULL;
910
        q->reading  = 0;
911
}
912
 
913
ssize_t videobuf_read_stream(struct file *file, struct videobuf_queue *q,
914
                             char *data, size_t count, loff_t *ppos,
915
                             int vbihack)
916
{
917
        unsigned int *fc, bytes;
918
        int err, retval;
919
        unsigned long flags;
920
 
921
        //down(&q->lock);
922
        retval = -EBUSY;
923
        if (q->streaming)
924
                goto done;
925
        if (!q->reading) {
926
                retval = videobuf_read_start(file,q);
927
                if (retval < 0)
928
                        goto done;
929
        }
930
 
931
        retval = 0;
932
        while (count > 0) {
933
                /* get / wait for data */
934
                if (NULL == q->read_buf) {
935
                        q->read_buf = list_entry(q->stream.next,
936
                                                 struct videobuf_buffer,
937
                                                 stream);
938
                        list_del(&q->read_buf->stream);
939
                        q->read_off = 0;
940
                }
941
                err = videobuf_waiton(q->read_buf,
942
                                      file->f_flags & O_NONBLOCK,1);
943
                if (err < 0) {
944
                        if (0 == retval)
945
                                retval = err;
946
                        break;
947
                }
948
 
949
                if (q->read_buf->state == STATE_DONE) {
950
                        if (vbihack) {
951
                                /* dirty, undocumented hack -- pass the frame counter
952
                                 * within the last four bytes of each vbi data block.
953
                                 * We need that one to maintain backward compatibility
954
                                 * to all vbi decoding software out there ... */
955
                                fc  = (unsigned int*)q->read_buf->dma.vmalloc;
956
                                fc += (q->read_buf->size>>2) -1;
957
                                *fc = q->read_buf->field_count >> 1;
958
                                dprintk(1,"vbihack: %d\n",*fc);
959
                        }
960
 
961
                        /* copy stuff */
962
                        bytes = count;
963
                        if (bytes > q->read_buf->size - q->read_off)
964
                                bytes = q->read_buf->size - q->read_off;
965
                        if (copy_to_user(data + retval,
966
                                         q->read_buf->dma.vmalloc + q->read_off,
967
                                         bytes)) {
968
                                if (0 == retval)
969
                                        retval = -EFAULT;
970
                                break;
971
                        }
972
                        count       -= bytes;
973
                        retval      += bytes;
974
                        q->read_off += bytes;
975
                } else {
976
                        /* some error -- skip buffer */
977
                        q->read_off = q->read_buf->size;
978
                }
979
 
980
                /* requeue buffer when done with copying */
981
                if (q->read_off == q->read_buf->size) {
982
                        list_add_tail(&q->read_buf->stream,
983
                                      &q->stream);
984
                        spin_lock_irqsave(q->irqlock,flags);
985
                        q->ops->buf_queue(file,q->read_buf);
986
                        spin_unlock_irqrestore(q->irqlock,flags);
987
                        q->read_buf = NULL;
988
                }
989
        }
990
 
991
 done:
992
        //up(&q->lock);
993
        return retval;
994
}
995
 
996
unsigned int videobuf_poll_stream(struct file *file,
997
                                  struct videobuf_queue *q,
998
                                  poll_table *wait)
999
{
1000
        struct videobuf_buffer *buf = NULL;
1001
        unsigned int rc = 0;
1002
 
1003
        //down(&q->lock);
1004
        if (q->streaming) {
1005
                if (!list_empty(&q->stream))
1006
                        buf = list_entry(q->stream.next,
1007
                                         struct videobuf_buffer, stream);
1008
        } else {
1009
                if (!q->reading)
1010
                        videobuf_read_start(file,q);
1011
                if (!q->reading) {
1012
                        rc = POLLERR;
1013
                } else if (NULL == q->read_buf) {
1014
                        q->read_buf = list_entry(q->stream.next,
1015
                                                 struct videobuf_buffer,
1016
                                                 stream);
1017
                        list_del(&q->read_buf->stream);
1018
                        q->read_off = 0;
1019
                }
1020
                buf = q->read_buf;
1021
        }
1022
        if (!buf)
1023
                rc = POLLERR;
1024
 
1025
        if (0 == rc) {
1026
                poll_wait(file, &buf->done, wait);
1027
                if (buf->state == STATE_DONE ||
1028
                    buf->state == STATE_ERROR)
1029
                        rc = POLLIN|POLLRDNORM;
1030
        }
1031
        //up(&q->lock);
1032
        return rc;
1033
}
1034
 
1035
/* --------------------------------------------------------------------- */
1036
 
1037
static void
1038
videobuf_vm_open(struct vm_area_struct *vma)
1039
{
1040
        struct videobuf_mapping *map = vma->vm_private_data;
1041
 
1042
        dprintk(2,"vm_open %p [count=%d,vma=%08lx-%08lx]\n",map,
1043
                map->count,vma->vm_start,vma->vm_end);
1044
        map->count++;
1045
}
1046
 
1047
static void
1048
videobuf_vm_close(struct vm_area_struct *vma)
1049
{
1050
        struct videobuf_mapping *map = vma->vm_private_data;
1051
        int i;
1052
 
1053
        dprintk(2,"vm_close %p [count=%d,vma=%08lx-%08lx]\n",map,
1054
                map->count,vma->vm_start,vma->vm_end);
1055
 
1056
        /* down(&fh->lock); FIXME */
1057
        map->count--;
1058
        if (0 == map->count) {
1059
                dprintk(1,"munmap %p\n",map);
1060
                for (i = 0; i < VIDEO_MAX_FRAME; i++) {
1061
                        if (NULL == map->q->bufs[i])
1062
                                continue;
1063
                        if (map->q->bufs[i])
1064
                                ;
1065
                        if (map->q->bufs[i]->map != map)
1066
                                continue;
1067
                        map->q->bufs[i]->map   = NULL;
1068
                        map->q->bufs[i]->baddr = 0;
1069
                        map->q->ops->buf_release(vma->vm_file,map->q->bufs[i]);
1070
                }
1071
                kfree(map);
1072
        }
1073
        /* up(&fh->lock); FIXME */
1074
        return;
1075
}
1076
 
1077
/*
1078
 * Get a anonymous page for the mapping.  Make sure we can DMA to that
1079
 * memory location with 32bit PCI devices (i.e. don't use highmem for
1080
 * now ...).  Bounce buffers don't work very well for the data rates
1081
 * video capture has.
1082
 */
1083
static struct page*
1084
videobuf_vm_nopage(struct vm_area_struct *vma, unsigned long vaddr,
1085
                  int write_access)
1086
{
1087
        struct page *page;
1088
 
1089
        dprintk(3,"nopage: fault @ %08lx [vma %08lx-%08lx]\n",
1090
                vaddr,vma->vm_start,vma->vm_end);
1091
        if (vaddr > vma->vm_end)
1092
                return NOPAGE_SIGBUS;
1093
        page = kmalloc(sizeof(struct page),GFP_KERNEL);
1094
        if (!page)
1095
                return NOPAGE_OOM;
1096
        //clear_user_page(page_address(page), vaddr, page);
1097
        return page;
1098
}
1099
 
1100
static struct vm_operations_struct videobuf_vm_ops =
1101
{
1102
        .open     = videobuf_vm_open,
1103
        .close    = videobuf_vm_close,
1104
        .nopage   = videobuf_vm_nopage,
1105
};
1106
 
1107
int videobuf_mmap_setup(struct file *file, struct videobuf_queue *q,
1108
                        unsigned int bcount, unsigned int bsize,
1109
                        enum v4l2_memory memory)
1110
{
1111
        unsigned int i;
1112
        int err;
1113
 
1114
        err = videobuf_mmap_free(file,q);
1115
        if (0 != err)
1116
                return err;
1117
 
1118
        for (i = 0; i < bcount; i++) {
1119
                q->bufs[i] = videobuf_alloc(q->msize);
1120
                q->bufs[i]->i      = i;
1121
                q->bufs[i]->memory = memory;
1122
                q->bufs[i]->bsize  = bsize;
1123
                switch (memory) {
1124
                case V4L2_MEMORY_MMAP:
1125
                        q->bufs[i]->boff  = bsize * i;
1126
                        break;
1127
                case V4L2_MEMORY_USERPTR:
1128
                case V4L2_MEMORY_OVERLAY:
1129
                        /* nothing */
1130
                        break;
1131
                };
1132
        }
1133
        dprintk(1,"mmap setup: %d buffers, %d bytes each\n",
1134
                bcount,bsize);
1135
        return 0;
1136
}
1137
 
1138
int videobuf_mmap_free(struct file *file, struct videobuf_queue *q)
1139
{
1140
        int i;
1141
 
1142
        for (i = 0; i < VIDEO_MAX_FRAME; i++)
1143
                if (q->bufs[i] && q->bufs[i]->map)
1144
                        return -EBUSY;
1145
        for (i = 0; i < VIDEO_MAX_FRAME; i++) {
1146
                if (NULL == q->bufs[i])
1147
                        continue;
1148
                q->ops->buf_release(file,q->bufs[i]);
1149
                kfree(q->bufs[i]);
1150
                q->bufs[i] = NULL;
1151
        }
1152
        return 0;
1153
}
1154
 
1155
int videobuf_mmap_mapper(struct vm_area_struct *vma,
1156
                         struct videobuf_queue *q)
1157
{
1158
        struct videobuf_mapping *map;
1159
        unsigned int first,last,size,i;
1160
        int retval;
1161
 
1162
        //down(&q->lock);
1163
 
1164
        retval = -EINVAL;
1165
        if (!(vma->vm_flags & VM_WRITE)) {
1166
                dprintk(1,"mmap app bug: PROT_WRITE please\n");
1167
                goto done;
1168
        }
1169
        if (!(vma->vm_flags & VM_SHARED)) {
1170
                dprintk(1,"mmap app bug: MAP_SHARED please\n");
1171
                goto done;
1172
        }
1173
 
1174
        /* look for first buffer to map */
1175
        for (first = 0; first < VIDEO_MAX_FRAME; first++) {
1176
                if (NULL == q->bufs[first])
1177
                        continue;
1178
                if (V4L2_MEMORY_MMAP != q->bufs[first]->memory)
1179
                        continue;
1180
                if (q->bufs[first]->boff == (vma->vm_pgoff << PAGE_SHIFT))
1181
                        break;
1182
        }
1183
        if (VIDEO_MAX_FRAME == first) {
1184
                dprintk(1,"mmap app bug: offset invalid [offset=0x%lx]\n",
1185
                        (vma->vm_pgoff << PAGE_SHIFT));
1186
                goto done;
1187
        }
1188
 
1189
        /* look for last buffer to map */
1190
        for (size = 0, last = first; last < VIDEO_MAX_FRAME; last++) {
1191
                if (NULL == q->bufs[last])
1192
                        continue;
1193
                if (V4L2_MEMORY_MMAP != q->bufs[last]->memory)
1194
                        continue;
1195
                if (q->bufs[last]->map) {
1196
                        retval = -EBUSY;
1197
                        goto done;
1198
                }
1199
                size += q->bufs[last]->bsize;
1200
                if (size == (vma->vm_end - vma->vm_start))
1201
                        break;
1202
        }
1203
        if (VIDEO_MAX_FRAME == last) {
1204
                dprintk(1,"mmap app bug: size invalid [size=0x%lx]\n",
1205
                        (vma->vm_end - vma->vm_start));
1206
                goto done;
1207
        }
1208
 
1209
        /* create mapping + update buffer list */
1210
        retval = -ENOMEM;
1211
        map = kmalloc(sizeof(struct videobuf_mapping),GFP_KERNEL);
1212
        if (NULL == map)
1213
                goto done;
1214
        for (size = 0, i = first; i <= last; size += q->bufs[i++]->bsize) {
1215
                q->bufs[i]->map   = map;
1216
                q->bufs[i]->baddr = vma->vm_start + size;
1217
        }
1218
        map->count    = 1;
1219
        map->start    = vma->vm_start;
1220
        map->end      = vma->vm_end;
1221
        map->q        = q;
1222
        vma->vm_ops   = &videobuf_vm_ops;
1223
        vma->vm_flags |= VM_DONTEXPAND;
1224
        vma->vm_flags &= ~VM_IO; /* using shared anonymous pages */
1225
        vma->vm_private_data = map;
1226
        dprintk(1,"mmap %p: %08lx-%08lx pgoff %08lx bufs %d-%d\n",
1227
                map,vma->vm_start,vma->vm_end,vma->vm_pgoff,first,last);
1228
        retval = 0;
1229
 
1230
 done:
1231
        //up(&q->lock);
1232
        return retval;
1233
}
1234
 
1235
/* --------------------------------------------------------------------- */
1236
 
1237
EXPORT_SYMBOL_GPL(videobuf_vmalloc_to_sg);
1238
EXPORT_SYMBOL_GPL(videobuf_lock);
1239
EXPORT_SYMBOL_GPL(videobuf_unlock);
1240
 
1241
EXPORT_SYMBOL_GPL(videobuf_dma_init_user);
1242
EXPORT_SYMBOL_GPL(videobuf_dma_init_kernel);
1243
EXPORT_SYMBOL_GPL(videobuf_dma_init_overlay);
1244
EXPORT_SYMBOL_GPL(videobuf_dma_pci_map);
1245
EXPORT_SYMBOL_GPL(videobuf_dma_pci_sync);
1246
EXPORT_SYMBOL_GPL(videobuf_dma_pci_unmap);
1247
EXPORT_SYMBOL_GPL(videobuf_dma_free);
1248
 
1249
EXPORT_SYMBOL_GPL(videobuf_alloc);
1250
EXPORT_SYMBOL_GPL(videobuf_waiton);
1251
EXPORT_SYMBOL_GPL(videobuf_iolock);
1252
 
1253
EXPORT_SYMBOL_GPL(videobuf_queue_init);
1254
EXPORT_SYMBOL_GPL(videobuf_queue_cancel);
1255
EXPORT_SYMBOL_GPL(videobuf_queue_is_busy);
1256
 
1257
EXPORT_SYMBOL_GPL(videobuf_next_field);
1258
EXPORT_SYMBOL_GPL(videobuf_status);
1259
EXPORT_SYMBOL_GPL(videobuf_reqbufs);
1260
EXPORT_SYMBOL_GPL(videobuf_querybuf);
1261
EXPORT_SYMBOL_GPL(videobuf_qbuf);
1262
EXPORT_SYMBOL_GPL(videobuf_dqbuf);
1263
EXPORT_SYMBOL_GPL(videobuf_streamon);
1264
EXPORT_SYMBOL_GPL(videobuf_streamoff);
1265
 
1266
EXPORT_SYMBOL_GPL(videobuf_read_start);
1267
EXPORT_SYMBOL_GPL(videobuf_read_stop);
1268
EXPORT_SYMBOL_GPL(videobuf_read_stream);
1269
EXPORT_SYMBOL_GPL(videobuf_read_one);
1270
EXPORT_SYMBOL_GPL(videobuf_poll_stream);
1271
 
1272
EXPORT_SYMBOL_GPL(videobuf_mmap_setup);
1273
EXPORT_SYMBOL_GPL(videobuf_mmap_free);
1274
EXPORT_SYMBOL_GPL(videobuf_mmap_mapper);
1275
 
1276
/*
1277
 * Local variables:
1278
 * c-basic-offset: 8
1279
 * End:
1280
 */