This is it! the ultimate last step, the vb2 conversion.

Signed-off-by: Corentin Labbe <cla...@baylibre.com>
---
 drivers/staging/media/zoran/Kconfig        |    2 +-
 drivers/staging/media/zoran/zoran.h        |   83 +-
 drivers/staging/media/zoran/zoran_card.c   |   45 +-
 drivers/staging/media/zoran/zoran_device.c |  488 ++-----
 drivers/staging/media/zoran/zoran_driver.c | 1453 +-------------------
 5 files changed, 137 insertions(+), 1934 deletions(-)

diff --git a/drivers/staging/media/zoran/Kconfig 
b/drivers/staging/media/zoran/Kconfig
index ddf38a931c01..492507030276 100644
--- a/drivers/staging/media/zoran/Kconfig
+++ b/drivers/staging/media/zoran/Kconfig
@@ -1,6 +1,6 @@
 config VIDEO_ZORAN
        tristate "Zoran ZR36057/36067 Video For Linux (Deprecated)"
-       depends on PCI && I2C_ALGOBIT && VIDEO_V4L2 && VIRT_TO_BUS
+       depends on PCI && I2C_ALGOBIT && VIDEO_V4L2
        depends on !ALPHA
        select VIDEOBUF2_DMA_CONTIG
        help
diff --git a/drivers/staging/media/zoran/zoran.h 
b/drivers/staging/media/zoran/zoran.h
index fd27d1968e60..372fadfd9a01 100644
--- a/drivers/staging/media/zoran/zoran.h
+++ b/drivers/staging/media/zoran/zoran.h
@@ -20,7 +20,6 @@
 
 #include <media/v4l2-device.h>
 #include <media/v4l2-ctrls.h>
-#include <media/v4l2-fh.h>
 #include <media/videobuf2-core.h>
 #include <media/videobuf2-v4l2.h>
 #include <media/videobuf2-dma-contig.h>
@@ -29,13 +28,6 @@
 #define ZR_NORM_NTSC 1
 #define ZR_NORM_SECAM 2
 
-struct zoran_sync {
-       unsigned long frame;    /* number of buffer that has been free'd */
-       unsigned long length;   /* number of code bytes in buffer (capture 
only) */
-       unsigned long seq;      /* frame sequence number */
-       u64 ts;                 /* timestamp */
-};
-
 struct zr_buffer {
        /* common v4l buffer stuff -- must be first */
        struct vb2_v4l2_buffer          vbuf;
@@ -111,18 +103,10 @@ enum zoran_codec_mode {
        BUZ_MODE_STILL_DECOMPRESS       /* still frame conversion */
 };
 
-enum zoran_buffer_state {
-       BUZ_STATE_USER,         /* buffer is owned by application */
-       BUZ_STATE_PEND,         /* buffer is queued in pend[] ready to feed to 
I/O */
-       BUZ_STATE_DMA,          /* buffer is queued in dma[] for I/O */
-       BUZ_STATE_DONE          /* buffer is ready to return to application */
-};
-
 enum zoran_map_mode {
        ZORAN_MAP_MODE_NONE,
        ZORAN_MAP_MODE_RAW,
        ZORAN_MAP_MODE_JPG_REC,
-#define ZORAN_MAP_MODE_JPG ZORAN_MAP_MODE_JPG_REC
        ZORAN_MAP_MODE_JPG_PLAY,
 };
 
@@ -174,45 +158,6 @@ struct zoran_jpg_settings {
        struct v4l2_jpegcompression jpg_comp;   /* JPEG-specific capture 
settings */
 };
 
-struct zoran_fh;
-
-struct zoran_mapping {
-       struct zoran_fh *fh;
-       atomic_t count;
-};
-
-struct zoran_buffer {
-       struct zoran_mapping *map;
-       enum zoran_buffer_state state;  /* state: unused/pending/dma/done */
-       struct zoran_sync bs;           /* DONE: info to return to application 
*/
-       union {
-               struct {
-                       __le32 *frag_tab;       /* addresses of frag table */
-                       u32 frag_tab_bus;       /* same value cached to save 
time in ISR */
-               } jpg;
-               struct {
-                       char *fbuffer;          /* virtual address of frame 
buffer */
-                       unsigned long fbuffer_phys;/* physical address of frame 
buffer */
-                       unsigned long fbuffer_bus;/* bus address of frame 
buffer */
-               } v4l;
-       };
-};
-
-enum zoran_lock_activity {
-       ZORAN_FREE,             /* free for use */
-       ZORAN_ACTIVE,           /* active but unlocked */
-       ZORAN_LOCKED,           /* locked */
-};
-
-/* buffer collections */
-struct zoran_buffer_col {
-       enum zoran_lock_activity active;        /* feature currently in use? */
-       unsigned int num_buffers;
-       struct zoran_buffer buffer[MAX_FRAME];  /* buffers */
-       u8 allocated;           /* Flag if buffers are allocated */
-       u8 need_contiguous;     /* Flag if contiguous buffers are needed */
-       /* only applies to jpg buffers, raw buffers are always contiguous */
-};
 
 struct zoran;
 
@@ -220,10 +165,6 @@ struct zoran;
 struct zoran_fh {
        struct v4l2_fh fh;
        struct zoran *zr;
-
-       enum zoran_map_mode map_mode;           /* Flag which bufferset will 
map by next mmap() */
-
-       struct zoran_buffer_col buffers;        /* buffers' info */
 };
 
 struct card_info {
@@ -281,7 +222,6 @@ struct zoran {
        struct mutex lock;      /* file ops serialize lock */
 
        u8 initialized;         /* flag if zoran has been correctly initialized 
*/
-       int user;               /* number of current users */
        struct card_info card;
        const struct tvnorm *timing;
 
@@ -300,28 +240,12 @@ struct zoran {
        /* Current buffer params */
        unsigned int buffer_size;
 
-       wait_queue_head_t v4l_capq;
-
-       int v4l_memgrab_active; /* Memory grab is activated */
-
-       int v4l_grab_frame;     /* Frame number being currently grabbed */
-#define NO_GRAB_ACTIVE (-1)
-       unsigned long v4l_grab_seq;     /* Number of frames grabbed */
        struct zoran_v4l_settings v4l_settings; /* structure with a lot of 
things to play with */
 
-       /* V4L grab queue of frames pending */
-       unsigned long v4l_pend_head;
-       unsigned long v4l_pend_tail;
-       unsigned long v4l_sync_tail;
-       int v4l_pend[V4L_MAX_FRAME];
-       struct zoran_buffer_col v4l_buffers;    /* V4L buffers' info */
-
        /* Buz MJPEG parameters */
        enum zoran_codec_mode codec_mode;       /* status of codec */
        struct zoran_jpg_settings jpg_settings; /* structure with a lot of 
things to play with */
 
-       wait_queue_head_t jpg_capq;     /* wait here for grab to finish */
-
        /* grab queue counts/indices, mask with BUZ_MASK_STAT_COM before using 
as index */
        /* (dma_head - dma_tail) is number active in DMA, must be <= 
BUZ_NUM_STAT_COM */
        /* (value & BUZ_MASK_STAT_COM) corresponds to index in stat_com table */
@@ -338,13 +262,8 @@ struct zoran {
        /* zr36057's code buffer table */
        __le32 *stat_com;               /* stat_com[i] is indexed by 
dma_head/tail & BUZ_MASK_STAT_COM */
 
-       /* (value & BUZ_MASK_FRAME) corresponds to index in pend[] queue */
-       int jpg_pend[BUZ_MAX_FRAME];
-
-       /* array indexed by frame number */
-       struct zoran_buffer_col jpg_buffers;    /* MJPEG buffers' info */
-
        /* Additional stuff for testing */
+       unsigned int ghost_int;
        int jpeg_error;
        int intr_counter_GIRQ1;
        int intr_counter_GIRQ0;
diff --git a/drivers/staging/media/zoran/zoran_card.c 
b/drivers/staging/media/zoran/zoran_card.c
index fe52be4292fe..84a5d52517cd 100644
--- a/drivers/staging/media/zoran/zoran_card.c
+++ b/drivers/staging/media/zoran/zoran_card.c
@@ -10,25 +10,17 @@
  */
 
 #include <linux/delay.h>
-
-#include <linux/types.h>
 #include <linux/kernel.h>
 #include <linux/module.h>
-#include <linux/init.h>
-#include <linux/vmalloc.h>
 #include <linux/slab.h>
 
 #include <linux/i2c.h>
 #include <linux/i2c-algo-bit.h>
 #include <linux/videodev2.h>
 #include <linux/spinlock.h>
-#include <linux/sem.h>
-#include <linux/kmod.h>
-#include <linux/wait.h>
 
 #include <linux/pci.h>
 #include <linux/interrupt.h>
-#include <linux/mutex.h>
 #include <linux/io.h>
 #include <media/v4l2-common.h>
 #include <media/i2c/bt819.h>
@@ -814,29 +806,12 @@ void zoran_open_init_params(struct zoran *zr)
 {
        int i;
 
-       zr->v4l_memgrab_active = 0;
-       zr->v4l_grab_frame = NO_GRAB_ACTIVE;
-       zr->v4l_grab_seq = 0;
        zr->v4l_settings.width = 192;
        zr->v4l_settings.height = 144;
        zr->v4l_settings.format = &zoran_formats[7];    /* YUY2 - YUV-4:2:2 
packed */
-       zr->v4l_settings.bytesperline =
-           zr->v4l_settings.width *
-           ((zr->v4l_settings.format->depth + 7) / 8);
-
-       /* DMA ring stuff for V4L */
-       zr->v4l_pend_tail = 0;
-       zr->v4l_pend_head = 0;
-       zr->v4l_sync_tail = 0;
-       zr->v4l_buffers.active = ZORAN_FREE;
-       for (i = 0; i < VIDEO_MAX_FRAME; i++)
-               zr->v4l_buffers.buffer[i].state = BUZ_STATE_USER;       /* 
nothing going on */
-       zr->v4l_buffers.allocated = 0;
-
-       for (i = 0; i < BUZ_MAX_FRAME; i++)
-               zr->jpg_buffers.buffer[i].state = BUZ_STATE_USER;       /* 
nothing going on */
-       zr->jpg_buffers.active = ZORAN_FREE;
-       zr->jpg_buffers.allocated = 0;
+       zr->v4l_settings.bytesperline = zr->v4l_settings.width *
+               ((zr->v4l_settings.format->depth + 7) / 8);
+
        /* Set necessary params and call zoran_check_jpg_settings to set the 
defaults */
        zr->jpg_settings.decimation = 1;
        zr->jpg_settings.jpg_comp.quality = 50; /* default compression factor 8 
*/
@@ -868,14 +843,6 @@ static int zr36057_init(struct zoran *zr)
 
        pci_info(zr->pci_dev, "initializing card[%d]\n", zr->id);
 
-       /* default setup of all parameters which will persist between opens */
-       zr->user = 0;
-
-       init_waitqueue_head(&zr->v4l_capq);
-       init_waitqueue_head(&zr->jpg_capq);
-       zr->jpg_buffers.allocated = 0;
-       zr->v4l_buffers.allocated = 0;
-
        /* Avoid nonsense settings from user for default input/norm */
        if (default_norm < 0 || default_norm > 2)
                default_norm = 0;
@@ -951,8 +918,6 @@ static int zr36057_init(struct zoran *zr)
        video_set_drvdata(zr->video_dev, zr);
 
        zoran_init_hardware(zr);
-       if (zr36067_debug > 2)
-               detect_guest_activity(zr);
        if (!pass_through) {
                decoder_call(zr, video, s_stream, 0);
                encoder_call(zr, video, s_routing, 2, 0, 0);
@@ -1279,10 +1244,8 @@ static int zoran_probe(struct pci_dev *pdev, const 
struct pci_device_id *ent)
        }
 
        /* take care of Natoma chipset and a revision 1 zr36057 */
-       if ((pci_pci_problems & PCIPCI_NATOMA) && zr->revision <= 1) {
-               zr->jpg_buffers.need_contiguous = 1;
+       if ((pci_pci_problems & PCIPCI_NATOMA) && zr->revision <= 1)
                pci_info(zr->pci_dev, "ZR36057/Natoma bug, max. buffer size is 
128K\n");
-       }
 
        if (zr36057_init(zr) < 0)
                goto zr_detach_vfe;
diff --git a/drivers/staging/media/zoran/zoran_device.c 
b/drivers/staging/media/zoran/zoran_device.c
index c090d7166caa..1fe91e16658b 100644
--- a/drivers/staging/media/zoran/zoran_device.c
+++ b/drivers/staging/media/zoran/zoran_device.c
@@ -12,9 +12,6 @@
 #include <linux/types.h>
 #include <linux/kernel.h>
 #include <linux/module.h>
-#include <linux/vmalloc.h>
-#include <linux/ktime.h>
-#include <linux/sched/signal.h>
 
 #include <linux/interrupt.h>
 #include <linux/i2c.h>
@@ -22,13 +19,12 @@
 #include <linux/videodev2.h>
 #include <media/v4l2-common.h>
 #include <linux/spinlock.h>
-#include <linux/sem.h>
 
 #include <linux/pci.h>
 #include <linux/delay.h>
 #include <linux/wait.h>
+#include <linux/dma-mapping.h>
 
-#include <asm/byteorder.h>
 #include <linux/io.h>
 
 #include "videocodec.h"
@@ -54,6 +50,7 @@ static bool lml33dpath;               /* default = 0
 module_param(lml33dpath, bool, 0644);
 MODULE_PARM_DESC(lml33dpath, "Use digital path capture mode (on LML33 cards)");
 
+int zr_set_buf(struct zoran *zr);
 /*
  * initialize video front end
  */
@@ -114,6 +111,7 @@ int post_office_wait(struct zoran *zr)
 //      while (((por = btread(ZR36057_POR)) & (ZR36057_POR_POPen | 
ZR36057_POR_POTime)) == ZR36057_POR_POPen) {
        while ((por = btread(ZR36057_POR)) & ZR36057_POR_POPen) {
                /* wait for something to happen */
+               /* TODO add timeout */
        }
        if ((por & ZR36057_POR_POTime) && !zr->card.gws_not_connected) {
                /* In LML33/BUZ \GWS line is not connected, so it has always 
timeout set */
@@ -422,42 +420,16 @@ void zr36057_set_memgrab(struct zoran *zr, int mode)
                zr36057_set_vfe(zr, zr->v4l_settings.width,
                                zr->v4l_settings.height,
                                zr->v4l_settings.format);
-
-               zr->v4l_memgrab_active = 1;
        } else {
                /* switch off VSync interrupts */
                btand(~zr->card.vsync_int, ZR36057_ICR);        // SW
 
-               zr->v4l_memgrab_active = 0;
-               zr->v4l_grab_frame = NO_GRAB_ACTIVE;
-
                /* re-enable grabbing to screen if it was running */
                btand(~ZR36057_VDCR_VidEn, ZR36057_VDCR);
                btand(~ZR36057_VSSFGR_SnapShot, ZR36057_VSSFGR);
        }
 }
 
-int wait_grab_pending(struct zoran *zr)
-{
-       unsigned long flags;
-
-       /* wait until all pending grabs are finished */
-
-       if (!zr->v4l_memgrab_active)
-               return 0;
-
-       wait_event_interruptible(zr->v4l_capq,
-                                (zr->v4l_pend_tail == zr->v4l_pend_head));
-       if (signal_pending(current))
-               return -ERESTARTSYS;
-
-       spin_lock_irqsave(&zr->spinlock, flags);
-       zr36057_set_memgrab(zr, 0);
-       spin_unlock_irqrestore(&zr->spinlock, flags);
-
-       return 0;
-}
-
 /*****************************************************************************
  *                                                                           *
  *  Set up the Buz-specific MJPEG part                                       *
@@ -501,9 +473,6 @@ static void init_jpeg_queue(struct zoran *zr)
        zr->jpg_err_seq = 0;
        zr->jpg_err_shift = 0;
        zr->jpg_queued_num = 0;
-       for (i = 0; i < zr->jpg_buffers.num_buffers; i++)
-               zr->jpg_buffers.buffer[i].state = BUZ_STATE_USER;       /* 
nothing going on */
-
        for (i = 0; i < BUZ_NUM_STAT_COM; i++)
                zr->stat_com[i] = cpu_to_le32(1);       /* mark as unavailable 
to zr36057 */
 }
@@ -605,50 +574,6 @@ static void zr36057_set_jpg(struct zoran *zr, enum 
zoran_codec_mode mode)
        zr36057_adjust_vfe(zr, mode);
 }
 
-void print_interrupts(struct zoran *zr)
-{
-       int res, noerr = 0;
-
-       pr_info("%s: interrupts received:", ZR_DEVNAME(zr));
-       res = zr->field_counter;
-       if (res < -1 || res > 1)
-               printk(KERN_CONT " FD:%d", res);
-       res = zr->intr_counter_GIRQ1;
-       if (res != 0) {
-               printk(KERN_CONT " GIRQ1:%d", res);
-               noerr++;
-       }
-       res = zr->intr_counter_GIRQ0;
-       if (res != 0) {
-               printk(KERN_CONT " GIRQ0:%d", res);
-               noerr++;
-       }
-       res = zr->intr_counter_CodRepIRQ;
-       if (res != 0) {
-               printk(KERN_CONT " CodRepIRQ:%d", res);
-               noerr++;
-       }
-       res = zr->intr_counter_JPEGRepIRQ;
-       if (res != 0) {
-               printk(KERN_CONT " JPEGRepIRQ:%d", res);
-               noerr++;
-       }
-       if (zr->JPEG_max_missed) {
-               printk(KERN_CONT " JPEG delays: max=%d min=%d", 
zr->JPEG_max_missed,
-                      zr->JPEG_min_missed);
-       }
-       if (zr->END_event_missed) {
-               printk(KERN_CONT " ENDs missed: %d", zr->END_event_missed);
-       }
-       //if (zr->jpg_queued_num) {
-       printk(KERN_CONT " queue_state=%ld/%ld/%ld/%ld", zr->jpg_que_tail,
-              zr->jpg_dma_tail, zr->jpg_dma_head, zr->jpg_que_head);
-       //}
-       if (!noerr)
-               printk(KERN_CONT ": no interrupts detected.");
-       printk(KERN_CONT "\n");
-}
-
 void clear_interrupt_counters(struct zoran *zr)
 {
        zr->intr_counter_GIRQ1 = 0;
@@ -870,37 +795,61 @@ void zoran_feed_stat_com(struct zoran *zr)
 {
        /* move frames from pending queue to DMA */
 
-       int frame, i, max_stat_com;
+       int i, max_stat_com;
+       struct zr_buffer *buf;
+       struct vb2_v4l2_buffer *vbuf;
+       dma_addr_t phys_addr = 0;
+       unsigned long flags;
+       unsigned long payload;
 
        max_stat_com =
            (zr->jpg_settings.TmpDcm ==
             1) ? BUZ_NUM_STAT_COM : (BUZ_NUM_STAT_COM >> 1);
 
-       while ((zr->jpg_dma_head - zr->jpg_dma_tail) < max_stat_com &&
-              zr->jpg_dma_head < zr->jpg_que_head) {
-               frame = zr->jpg_pend[zr->jpg_dma_head & BUZ_MASK_FRAME];
+       spin_lock_irqsave(&zr->queued_bufs_lock, flags);
+       while ((zr->jpg_dma_head - zr->jpg_dma_tail) < max_stat_com) {
+               buf = list_first_entry_or_null(&zr->queued_bufs, struct 
zr_buffer, queue);
+               if (!buf) {
+                       pci_err(zr->pci_dev, "No buffer available to queue\n");
+                       spin_unlock_irqrestore(&zr->queued_bufs_lock, flags);
+                       return;
+               }
+               list_del(&buf->queue);
+               zr->buf_in_reserve--;
+               vbuf = &buf->vbuf;
+               vbuf->vb2_buf.state = VB2_BUF_STATE_ACTIVE;
+               phys_addr = vb2_dma_contig_plane_dma_addr(&vbuf->vb2_buf, 0);
+               payload = vb2_get_plane_payload(&vbuf->vb2_buf, 0);
+               if (payload == 0)
+                       payload = zr->buffer_size;
                if (zr->jpg_settings.TmpDcm == 1) {
                        /* fill 1 stat_com entry */
                        i = (zr->jpg_dma_head -
                             zr->jpg_err_shift) & BUZ_MASK_STAT_COM;
                        if (!(zr->stat_com[i] & cpu_to_le32(1)))
                                break;
-                       zr->stat_com[i] =
-                           
cpu_to_le32(zr->jpg_buffers.buffer[frame].jpg.frag_tab_bus);
+                       zr->stat_comb[i * 2] = cpu_to_le32(phys_addr);
+                       zr->stat_comb[i * 2 + 1] = cpu_to_le32((payload >> 1) | 
1);
+                       zr->inuse[i] = buf;
+                       zr->stat_com[i] = cpu_to_le32(zr->p_scb + i * 2 * 4);
                } else {
                        /* fill 2 stat_com entries */
                        i = ((zr->jpg_dma_head -
                              zr->jpg_err_shift) & 1) * 2;
                        if (!(zr->stat_com[i] & cpu_to_le32(1)))
                                break;
-                       zr->stat_com[i] =
-                           
cpu_to_le32(zr->jpg_buffers.buffer[frame].jpg.frag_tab_bus);
-                       zr->stat_com[i + 1] =
-                           
cpu_to_le32(zr->jpg_buffers.buffer[frame].jpg.frag_tab_bus);
+                       zr->stat_com[i] = cpu_to_le32(zr->p_scb + i * 2 * 4);
+                       zr->stat_com[i + 1] = cpu_to_le32(zr->p_scb + i * 2 * 
4);
+
+                       zr->stat_comb[i * 2] = cpu_to_le32(phys_addr);
+                       zr->stat_comb[i * 2 + 1] = cpu_to_le32((payload >> 1) | 
1);
+
+                       zr->inuse[i] = buf;
+                       zr->inuse[i + 1] = NULL;
                }
-               zr->jpg_buffers.buffer[frame].state = BUZ_STATE_DMA;
                zr->jpg_dma_head++;
        }
+       spin_unlock_irqrestore(&zr->queued_bufs_lock, flags);
        if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS)
                zr->jpg_queued_num++;
 }
@@ -914,8 +863,10 @@ static void zoran_reap_stat_com(struct zoran *zr)
        u32 stat_com;
        unsigned int seq;
        unsigned int dif;
-       struct zoran_buffer *buffer;
-       int frame;
+       unsigned long flags;
+       struct zr_buffer *buf;
+       unsigned int size = 0;
+       u32 fcnt;
 
        /* In motion decompress we don't have a hardware frame counter,
         * we just count the interrupts here */
@@ -923,347 +874,78 @@ static void zoran_reap_stat_com(struct zoran *zr)
        if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS)
                zr->jpg_seq_num++;
 
+       spin_lock_irqsave(&zr->queued_bufs_lock, flags);
        while (zr->jpg_dma_tail < zr->jpg_dma_head) {
                if (zr->jpg_settings.TmpDcm == 1)
-                       i = (zr->jpg_dma_tail -
-                            zr->jpg_err_shift) & BUZ_MASK_STAT_COM;
+                       i = (zr->jpg_dma_tail - zr->jpg_err_shift) & 
BUZ_MASK_STAT_COM;
                else
-                       i = ((zr->jpg_dma_tail -
-                             zr->jpg_err_shift) & 1) * 2 + 1;
+                       i = ((zr->jpg_dma_tail - zr->jpg_err_shift) & 1) * 2 + 
1;
 
                stat_com = le32_to_cpu(zr->stat_com[i]);
-
-               if ((stat_com & 1) == 0)
+               if ((stat_com & 1) == 0) {
+                       spin_unlock_irqrestore(&zr->queued_bufs_lock, flags);
                        return;
+               }
+
+               fcnt = (stat_com & GENMASK(31, 24)) >> 24;
+               size = (stat_com & GENMASK(22, 1)) >> 1;
 
-               frame = zr->jpg_pend[zr->jpg_dma_tail & BUZ_MASK_FRAME];
-               buffer = &zr->jpg_buffers.buffer[frame];
-               buffer->bs.ts = ktime_get_ns();
+               buf = zr->inuse[i];
+               buf->vbuf.vb2_buf.timestamp = ktime_get_ns();
 
                if (zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) {
-                       buffer->bs.length = (stat_com & 0x7fffff) >> 1;
+                       vb2_set_plane_payload(&buf->vbuf.vb2_buf, 0, size);
 
                        /* update sequence number with the help of the counter 
in stat_com */
-
-                       seq = ((stat_com >> 24) + zr->jpg_err_seq) & 0xff;
+                       seq = (fcnt + zr->jpg_err_seq) & 0xff;
                        dif = (seq - zr->jpg_seq_num) & 0xff;
                        zr->jpg_seq_num += dif;
-               } else {
-                       buffer->bs.length = 0;
                }
-               buffer->bs.seq =
-                   zr->jpg_settings.TmpDcm ==
+               buf->vbuf.sequence = zr->jpg_settings.TmpDcm ==
                    2 ? (zr->jpg_seq_num >> 1) : zr->jpg_seq_num;
-               buffer->state = BUZ_STATE_DONE;
-
-               zr->jpg_dma_tail++;
-       }
-}
-
-static void zoran_restart(struct zoran *zr)
-{
-       /* Now the stat_comm buffer is ready for restart */
-       unsigned int status = 0;
-       int mode;
-
-       if (zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) {
-               decoder_call(zr, video, g_input_status, &status);
-               mode = CODEC_DO_COMPRESSION;
-       } else {
-               status = V4L2_IN_ST_NO_SIGNAL;
-               mode = CODEC_DO_EXPANSION;
-       }
-       if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS ||
-           !(status & V4L2_IN_ST_NO_SIGNAL)) {
-               /********** RESTART code *************/
-               jpeg_codec_reset(zr);
-               zr->codec->set_mode(zr->codec, mode);
-               zr36057_set_jpg(zr, zr->codec_mode);
-               jpeg_start(zr);
-
-               if (zr->num_errors <= 8)
-                       pci_info(zr->pci_dev, "Restart\n");
-
-               zr->JPEG_missed = 0;
-               zr->JPEG_error = 2;
-               /********** End RESTART code ***********/
-       }
-}
-
-static void error_handler(struct zoran *zr, u32 astat, u32 stat)
-{
-       int i;
-
-       /* This is JPEG error handling part */
-       if (zr->codec_mode != BUZ_MODE_MOTION_COMPRESS &&
-           zr->codec_mode != BUZ_MODE_MOTION_DECOMPRESS) {
-               return;
-       }
-
-       if ((stat & 1) == 0 &&
-           zr->codec_mode == BUZ_MODE_MOTION_COMPRESS &&
-           zr->jpg_dma_tail - zr->jpg_que_tail >= zr->jpg_buffers.num_buffers) 
{
-               /* No free buffers... */
-               zoran_reap_stat_com(zr);
-               zoran_feed_stat_com(zr);
-               wake_up_interruptible(&zr->jpg_capq);
-               zr->JPEG_missed = 0;
-               return;
-       }
-
-       if (zr->JPEG_error == 1) {
-               zoran_restart(zr);
-               return;
-       }
-
-       /*
-        * First entry: error just happened during normal operation
-        *
-        * In BUZ_MODE_MOTION_COMPRESS:
-        *
-        * Possible glitch in TV signal. In this case we should
-        * stop the codec and wait for good quality signal before
-        * restarting it to avoid further problems
-        *
-        * In BUZ_MODE_MOTION_DECOMPRESS:
-        *
-        * Bad JPEG frame: we have to mark it as processed (codec crashed
-        * and was not able to do it itself), and to remove it from queue.
-        */
-       btand(~ZR36057_JMC_Go_en, ZR36057_JMC);
-       udelay(1);
-       stat = stat | (post_office_read(zr, 7, 0) & 3) << 8;
-       btwrite(0, ZR36057_JPC);
-       btor(ZR36057_MCTCR_CFlush, ZR36057_MCTCR);
-       jpeg_codec_reset(zr);
-       jpeg_codec_sleep(zr, 1);
-       zr->JPEG_error = 1;
-       zr->num_errors++;
-
-       /* Report error */
-       if (zr36067_debug > 1 && zr->num_errors <= 8) {
-               long frame;
-               int j;
-
-               frame = zr->jpg_pend[zr->jpg_dma_tail & BUZ_MASK_FRAME];
-               pci_err(zr->pci_dev, "JPEG error stat=0x%08x(0x%08x) 
queue_state=%ld/%ld/%ld/%ld seq=%ld frame=%ld. Codec stopped. ",
-                       stat, zr->last_isr,
-                       zr->jpg_que_tail, zr->jpg_dma_tail,
-                       zr->jpg_dma_head, zr->jpg_que_head,
-                       zr->jpg_seq_num, frame);
-               pr_info("stat_com frames:");
-               for (j = 0; j < BUZ_NUM_STAT_COM; j++) {
-                       for (i = 0; i < zr->jpg_buffers.num_buffers; i++) {
-                               if (le32_to_cpu(zr->stat_com[j]) == 
zr->jpg_buffers.buffer[i].jpg.frag_tab_bus)
-                                       printk(KERN_CONT "% d->%d", j, i);
-                       }
-               }
-               printk(KERN_CONT "\n");
-       }
-       /* Find an entry in stat_com and rotate contents */
-       if (zr->jpg_settings.TmpDcm == 1)
-               i = (zr->jpg_dma_tail - zr->jpg_err_shift) & BUZ_MASK_STAT_COM;
-       else
-               i = ((zr->jpg_dma_tail - zr->jpg_err_shift) & 1) * 2;
-       if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS) {
-               /* Mimic zr36067 operation */
-               zr->stat_com[i] |= cpu_to_le32(1);
+               zr->inuse[i] = NULL;
                if (zr->jpg_settings.TmpDcm != 1)
-                       zr->stat_com[i + 1] |= cpu_to_le32(1);
-               /* Refill */
-               zoran_reap_stat_com(zr);
-               zoran_feed_stat_com(zr);
-               wake_up_interruptible(&zr->jpg_capq);
-               /* Find an entry in stat_com again after refill */
-               if (zr->jpg_settings.TmpDcm == 1)
-                       i = (zr->jpg_dma_tail - zr->jpg_err_shift) & 
BUZ_MASK_STAT_COM;
+                       buf->vbuf.field = zr->jpg_settings.odd_even ?
+                               V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM;
                else
-                       i = ((zr->jpg_dma_tail - zr->jpg_err_shift) & 1) * 2;
-       }
-       if (i) {
-               /* Rotate stat_comm entries to make current entry first */
-               int j;
-               __le32 bus_addr[BUZ_NUM_STAT_COM];
-
-               /* Here we are copying the stat_com array, which
-                * is already in little endian format, so
-                * no endian conversions here
-                */
-               memcpy(bus_addr, zr->stat_com, sizeof(bus_addr));
+                       buf->vbuf.field = zr->jpg_settings.odd_even ?
+                               V4L2_FIELD_SEQ_TB : V4L2_FIELD_SEQ_BT;
+               vb2_buffer_done(&buf->vbuf.vb2_buf, VB2_BUF_STATE_DONE);
 
-               for (j = 0; j < BUZ_NUM_STAT_COM; j++)
-                       zr->stat_com[j] = bus_addr[(i + j) & BUZ_MASK_STAT_COM];
-
-               zr->jpg_err_shift += i;
-               zr->jpg_err_shift &= BUZ_MASK_STAT_COM;
+               zr->jpg_dma_tail++;
        }
-       if (zr->codec_mode == BUZ_MODE_MOTION_COMPRESS)
-               zr->jpg_err_seq = zr->jpg_seq_num;      /* + 1; */
-       zoran_restart(zr);
+       spin_unlock_irqrestore(&zr->queued_bufs_lock, flags);
 }
 
 irqreturn_t zoran_irq(int irq, void *dev_id)
 {
-       u32 stat, astat;
-       int count = 0;
        struct zoran *zr = dev_id;
-       unsigned long flags;
-
-       spin_lock_irqsave(&zr->spinlock, flags);
-       while (1) {
-               /* get/clear interrupt status bits */
-               stat = count_reset_interrupt(zr);
-               astat = stat & IRQ_MASK;
-               if (!astat)
-                       break;
-               pr_debug("%s: astat: 0x%08x, mask: 0x%08x\n", __func__, astat, 
btread(ZR36057_ICR));
-               if (astat & zr->card.vsync_int) {       // SW
-
-                       if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS ||
-                           zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) {
-                               /* count missed interrupts */
-                               zr->JPEG_missed++;
-                       }
-                       //post_office_read(zr,1,0);
-                       /*
-                        * Interrupts may still happen when
-                        * zr->v4l_memgrab_active is switched off.
-                        * We simply ignore them
-                        */
-
-                       if (zr->v4l_memgrab_active) {
-                               /* A lot more checks should be here ... */
-                               if ((btread(ZR36057_VSSFGR) & 
ZR36057_VSSFGR_SnapShot) == 0)
-                                       pci_warn(zr->pci_dev, "BuzIRQ with 
SnapShot off ???\n");
-
-                               if (zr->v4l_grab_frame != NO_GRAB_ACTIVE) {
-                                       /* There is a grab on a frame going on, 
check if it has finished */
-                                       if ((btread(ZR36057_VSSFGR) & 
ZR36057_VSSFGR_FrameGrab) == 0) {
-                                               /* it is finished, notify the 
user */
-
-                                               
zr->v4l_buffers.buffer[zr->v4l_grab_frame].state = BUZ_STATE_DONE;
-                                               
zr->v4l_buffers.buffer[zr->v4l_grab_frame].bs.seq = zr->v4l_grab_seq;
-                                               
zr->v4l_buffers.buffer[zr->v4l_grab_frame].bs.ts = ktime_get_ns();
-                                               zr->v4l_grab_frame = 
NO_GRAB_ACTIVE;
-                                               zr->v4l_pend_tail++;
-                                       }
-                               }
-
-                               if (zr->v4l_grab_frame == NO_GRAB_ACTIVE)
-                                       wake_up_interruptible(&zr->v4l_capq);
-
-                               /* Check if there is another grab queued */
-
-                               if (zr->v4l_grab_frame == NO_GRAB_ACTIVE &&
-                                   zr->v4l_pend_tail != zr->v4l_pend_head) {
-                                       int frame = 
zr->v4l_pend[zr->v4l_pend_tail & V4L_MASK_FRAME];
-                                       u32 reg;
-
-                                       zr->v4l_grab_frame = frame;
-
-                                       /* Set zr36057 video front end and 
enable video */
-
-                                       /* Buffer address */
-
-                                       reg = 
zr->v4l_buffers.buffer[frame].v4l.fbuffer_bus;
-                                       btwrite(reg, ZR36057_VDTR);
-                                       if (zr->v4l_settings.height > 
BUZ_MAX_HEIGHT / 2)
-                                               reg += 
zr->v4l_settings.bytesperline;
-                                       btwrite(reg, ZR36057_VDBR);
-
-                                       /* video stride, status, and frame grab 
register */
-                                       reg = 0;
-                                       if (zr->v4l_settings.height > 
BUZ_MAX_HEIGHT / 2)
-                                               reg += 
zr->v4l_settings.bytesperline;
-                                       reg = (reg << 
ZR36057_VSSFGR_DispStride);
-                                       reg |= ZR36057_VSSFGR_VidOvf;
-                                       reg |= ZR36057_VSSFGR_SnapShot;
-                                       reg |= ZR36057_VSSFGR_FrameGrab;
-                                       btwrite(reg, ZR36057_VSSFGR);
-
-                                       btor(ZR36057_VDCR_VidEn, ZR36057_VDCR);
-                               }
-                       }
-
-                       /*
-                        * even if we don't grab, we do want to increment
-                        * the sequence counter to see lost frames
-                        */
-                       zr->v4l_grab_seq++;
-               }
-#if (IRQ_MASK & ZR36057_ISR_CodRepIRQ)
-               if (astat & ZR36057_ISR_CodRepIRQ) {
-                       zr->intr_counter_CodRepIRQ++;
-                       IDEBUG(printk(KERN_DEBUG "%s: ZR36057_ISR_CodRepIRQ\n", 
ZR_DEVNAME(zr)));
-                       btand(~ZR36057_ICR_CodRepIRQ, ZR36057_ICR);
-               }
-#endif                         /* (IRQ_MASK & ZR36057_ISR_CodRepIRQ) */
-
-#if (IRQ_MASK & ZR36057_ISR_JPEGRepIRQ)
-               if ((astat & ZR36057_ISR_JPEGRepIRQ) &&
-                   (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS ||
-                    zr->codec_mode == BUZ_MODE_MOTION_COMPRESS)) {
-                       if (zr36067_debug > 1 && (!zr->frame_num || 
zr->JPEG_error)) {
-                               char sv[BUZ_NUM_STAT_COM + 1];
-                               int i;
-
-                               pr_info("%s: first frame ready: state=0x%08x 
odd_even=%d field_per_buff=%d delay=%d\n",
-                                       ZR_DEVNAME(zr), stat, 
zr->jpg_settings.odd_even,
-                                      zr->jpg_settings.field_per_buff, 
zr->JPEG_missed);
-
-                               for (i = 0; i < BUZ_NUM_STAT_COM; i++)
-                                       sv[i] = le32_to_cpu(zr->stat_com[i]) & 
1 ? '1' : '0';
-                               sv[BUZ_NUM_STAT_COM] = 0;
-                               pr_info("%s: stat_com=%s 
queue_state=%ld/%ld/%ld/%ld\n",
-                                       ZR_DEVNAME(zr), sv, zr->jpg_que_tail, 
zr->jpg_dma_tail,
-                                      zr->jpg_dma_head, zr->jpg_que_head);
-                       } else {
-                               /* Get statistics */
-                               if (zr->JPEG_missed > zr->JPEG_max_missed)
-                                       zr->JPEG_max_missed = zr->JPEG_missed;
-                               if (zr->JPEG_missed < zr->JPEG_min_missed)
-                                       zr->JPEG_min_missed = zr->JPEG_missed;
-                       }
-
-                       if (zr36067_debug > 2 && zr->frame_num < 6) {
-                               int i;
+       u32 stat, astat;
 
-                               pr_info("%s: seq=%ld stat_com:", 
ZR_DEVNAME(zr), zr->jpg_seq_num);
-                               for (i = 0; i < 4; i++)
-                                       printk(KERN_CONT " %08x", 
le32_to_cpu(zr->stat_com[i]));
-                               printk(KERN_CONT "\n");
-                       }
-                       zr->frame_num++;
-                       zr->JPEG_missed = 0;
-                       zr->JPEG_error = 0;
-                       zoran_reap_stat_com(zr);
-                       zoran_feed_stat_com(zr);
-                       wake_up_interruptible(&zr->jpg_capq);
+       stat = count_reset_interrupt(zr);
+       astat = stat & IRQ_MASK;
+       if (astat & zr->card.vsync_int) {
+               if (zr->running == ZORAN_MAP_MODE_RAW) {
+                       if ((btread(ZR36057_VSSFGR) & ZR36057_VSSFGR_SnapShot) 
== 0)
+                               pci_warn(zr->pci_dev, "BuzIRQ with SnapShot off 
???\n");
+                       if ((btread(ZR36057_VSSFGR) & ZR36057_VSSFGR_FrameGrab) 
== 0)
+                               zr_set_buf(zr);
+                       return IRQ_HANDLED;
                }
-#endif                         /* (IRQ_MASK & ZR36057_ISR_JPEGRepIRQ) */
-
-               /* DATERR, too many fields missed, error processing */
-               if ((astat & zr->card.jpeg_int) ||
-                   zr->JPEG_missed > 25 ||
-                   zr->JPEG_error == 1 ||
-                   ((zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS) &&
-                    (zr->frame_num && (zr->JPEG_missed > 
zr->jpg_settings.field_per_buff)))) {
-                       error_handler(zr, astat, stat);
-               }
-
-               count++;
-               if (count > 10) {
-                       pci_warn(zr->pci_dev, "irq loop %d\n", count);
-                       if (count > 20) {
-                               btand(~ZR36057_ICR_IntPinEn, ZR36057_ICR);
-                               pci_err(zr->pci_dev, "IRQ lockup, cleared int 
mask\n");
-                               break;
+               if (astat & ZR36057_ISR_JPEGRepIRQ) {
+                       if (zr->codec_mode != BUZ_MODE_MOTION_DECOMPRESS &&
+                           zr->codec_mode != BUZ_MODE_MOTION_COMPRESS) {
+                               pci_err(zr->pci_dev, "JPG IRQ when not in good 
mode\n");
+                               return IRQ_HANDLED;
                        }
+               zr->frame_num++;
+               zoran_reap_stat_com(zr);
+               zoran_feed_stat_com(zr);
+               return IRQ_HANDLED;
                }
-               zr->last_isr = stat;
+               /* unused interrupts */
        }
-       spin_unlock_irqrestore(&zr->spinlock, flags);
-
+       zr->ghost_int++;
        return IRQ_HANDLED;
 }
 
diff --git a/drivers/staging/media/zoran/zoran_driver.c 
b/drivers/staging/media/zoran/zoran_driver.c
index a6fb41d03186..c5b2ccb00ca9 100644
--- a/drivers/staging/media/zoran/zoran_driver.c
+++ b/drivers/staging/media/zoran/zoran_driver.c
@@ -35,7 +35,6 @@
 #include <linux/delay.h>
 #include <linux/slab.h>
 #include <linux/pci.h>
-#include <linux/vmalloc.h>
 #include <linux/wait.h>
 
 #include <linux/interrupt.h>
@@ -50,7 +49,6 @@
 #include <media/v4l2-event.h>
 #include "videocodec.h"
 
-#include <asm/byteorder.h>
 #include <linux/io.h>
 #include <linux/uaccess.h>
 
@@ -159,234 +157,8 @@ static __u32 zoran_v4l2_calc_bufsize(struct 
zoran_jpg_settings *settings)
                return jpg_bufsize;
        if (result < 8192)
                return 8192;
-       return result;
-}
-
-/* forward references */
-static void v4l_fbuffer_free(struct zoran_fh *fh);
-static void jpg_fbuffer_free(struct zoran_fh *fh);
-
-/* Set mapping mode */
-static void map_mode_raw(struct zoran_fh *fh)
-{
-       struct zoran *zr = fh->zr;
-       fh->map_mode = ZORAN_MAP_MODE_RAW;
-       zr->buffer_size = v4l_bufsize;
-       fh->buffers.num_buffers = v4l_nbufs;
-}
-
-static void map_mode_jpg(struct zoran_fh *fh, int play)
-{
-       struct zoran *zr = fh->zr;
-
-       fh->map_mode = play ? ZORAN_MAP_MODE_JPG_PLAY : ZORAN_MAP_MODE_JPG_REC;
-       zr->buffer_size = jpg_bufsize;
-       fh->buffers.num_buffers = jpg_nbufs;
-}
-
-static inline const char *mode_name(enum zoran_map_mode mode)
-{
-       return mode == ZORAN_MAP_MODE_RAW ? "V4L" : "JPG";
-}
-
-/*
- *   Allocate the V4L grab buffers
- *
- *   These have to be pysically contiguous.
- */
-
-static int v4l_fbuffer_alloc(struct zoran_fh *fh)
-{
-       struct zoran *zr = fh->zr;
-       int i, off;
-       unsigned char *mem;
-
-       for (i = 0; i < fh->buffers.num_buffers; i++) {
-               if (fh->buffers.buffer[i].v4l.fbuffer)
-                       pci_warn(zr->pci_dev, "%s - buffer %d already 
allocated!?\n", __func__, i);
-
-               //udelay(20);
-               mem = kmalloc(zr->buffer_size, GFP_KERNEL | __GFP_NOWARN);
-               if (!mem) {
-                       pci_err(zr->pci_dev, "%s - kmalloc for V4L buf %d 
failed\n", __func__, i);
-                       v4l_fbuffer_free(fh);
-                       return -ENOBUFS;
-               }
-               fh->buffers.buffer[i].v4l.fbuffer = mem;
-               fh->buffers.buffer[i].v4l.fbuffer_phys = virt_to_phys(mem);
-               fh->buffers.buffer[i].v4l.fbuffer_bus = virt_to_bus(mem);
-               for (off = 0; off < zr->buffer_size;
-                    off += PAGE_SIZE)
-                       SetPageReserved(virt_to_page(mem + off));
-               pci_info(zr->pci_dev, "%s - V4L frame %d mem %p (bus: 
0x%llx)\n", __func__, i, mem,
-                        (unsigned long long)virt_to_bus(mem));
-       }
-
-       fh->buffers.allocated = 1;
-
-       return 0;
-}
-
-/* free the V4L grab buffers */
-static void v4l_fbuffer_free(struct zoran_fh *fh)
-{
-       struct zoran *zr = fh->zr;
-       int i, off;
-       unsigned char *mem;
-
-       pci_dbg(zr->pci_dev, "%s\n", __func__);
-
-       for (i = 0; i < fh->buffers.num_buffers; i++) {
-               if (!fh->buffers.buffer[i].v4l.fbuffer)
-                       continue;
-
-               mem = fh->buffers.buffer[i].v4l.fbuffer;
-               for (off = 0; off < zr->buffer_size;
-                    off += PAGE_SIZE)
-                       ClearPageReserved(virt_to_page(mem + off));
-               kfree(fh->buffers.buffer[i].v4l.fbuffer);
-               fh->buffers.buffer[i].v4l.fbuffer = NULL;
-       }
 
-       fh->buffers.allocated = 0;
-}
-
-/*
- *   Allocate the MJPEG grab buffers.
- *
- *   If a Natoma chipset is present and this is a revision 1 zr36057,
- *   each MJPEG buffer needs to be physically contiguous.
- *   (RJ: This statement is from Dave Perks' original driver,
- *   I could never check it because I have a zr36067)
- *
- *   RJ: The contents grab buffers needs never be accessed in the driver.
- *       Therefore there is no need to allocate them with vmalloc in order
- *       to get a contiguous virtual memory space.
- *       I don't understand why many other drivers first allocate them with
- *       vmalloc (which uses internally also get_zeroed_page, but delivers you
- *       virtual addresses) and then again have to make a lot of efforts
- *       to get the physical address.
- *
- *   Ben Capper:
- *       On big-endian architectures (such as ppc) some extra steps
- *       are needed. When reading and writing to the stat_com array
- *       and fragment buffers, the device expects to see little-
- *       endian values. The use of cpu_to_le32() and le32_to_cpu()
- *       in this function (and one or two others in zoran_device.c)
- *       ensure that these values are always stored in little-endian
- *       form, regardless of architecture. The zr36057 does Very Bad
- *       Things on big endian architectures if the stat_com array
- *       and fragment buffers are not little-endian.
- */
-
-static int jpg_fbuffer_alloc(struct zoran_fh *fh)
-{
-       struct zoran *zr = fh->zr;
-       int i, j, off;
-       u8 *mem;
-
-       for (i = 0; i < fh->buffers.num_buffers; i++) {
-               if (fh->buffers.buffer[i].jpg.frag_tab)
-                       pci_warn(zr->pci_dev, "%s - buffer %d already 
allocated!?\n", __func__, i);
-
-               /* Allocate fragment table for this buffer */
-
-               mem = (void *)get_zeroed_page(GFP_KERNEL);
-               if (!mem) {
-                       pci_err(zr->pci_dev, "%s - get_zeroed_page (frag_tab) 
failed for buffer %d\n", __func__, i);
-                       jpg_fbuffer_free(fh);
-                       return -ENOBUFS;
-               }
-               fh->buffers.buffer[i].jpg.frag_tab = (__le32 *)mem;
-               fh->buffers.buffer[i].jpg.frag_tab_bus = virt_to_bus(mem);
-
-               if (fh->buffers.need_contiguous) {
-                       mem = kmalloc(zr->buffer_size, GFP_KERNEL);
-                       if (!mem) {
-                               pci_err(zr->pci_dev, "%s - kmalloc failed for 
buffer %d\n", __func__, i);
-                               jpg_fbuffer_free(fh);
-                               return -ENOBUFS;
-                       }
-                       fh->buffers.buffer[i].jpg.frag_tab[0] =
-                               cpu_to_le32(virt_to_bus(mem));
-                       fh->buffers.buffer[i].jpg.frag_tab[1] =
-                               cpu_to_le32((zr->buffer_size >> 1) | 1);
-                       for (off = 0; off < zr->buffer_size; off += PAGE_SIZE)
-                               SetPageReserved(virt_to_page(mem + off));
-               } else {
-                       /* jpg_bufsize is already page aligned */
-                       for (j = 0; j < zr->buffer_size / PAGE_SIZE; j++) {
-                               mem = (void *)get_zeroed_page(GFP_KERNEL);
-                               if (!mem) {
-                                       pci_err(zr->pci_dev, "%s - 
get_zeroed_page failed for buffer %d\n", __func__, i);
-                                       jpg_fbuffer_free(fh);
-                                       return -ENOBUFS;
-                               }
-
-                               fh->buffers.buffer[i].jpg.frag_tab[2 * j] =
-                                       cpu_to_le32(virt_to_bus(mem));
-                               fh->buffers.buffer[i].jpg.frag_tab[2 * j + 1] =
-                                       cpu_to_le32((PAGE_SIZE >> 2) << 1);
-                               SetPageReserved(virt_to_page(mem));
-                       }
-
-                       fh->buffers.buffer[i].jpg.frag_tab[2 * j - 1] |= 
cpu_to_le32(1);
-               }
-       }
-
-       pci_dbg(zr->pci_dev, "%s - %d KB allocated\n", __func__,
-               (fh->buffers.num_buffers * zr->buffer_size) >> 10);
-
-       fh->buffers.allocated = 1;
-
-       return 0;
-}
-
-/* free the MJPEG grab buffers */
-static void jpg_fbuffer_free(struct zoran_fh *fh)
-{
-       struct zoran *zr = fh->zr;
-       int i, j, off;
-       unsigned char *mem;
-       __le32 frag_tab;
-       struct zoran_buffer *buffer;
-
-       pci_dbg(zr->pci_dev, "%s\n", __func__);
-
-       for (i = 0, buffer = &fh->buffers.buffer[0];
-            i < fh->buffers.num_buffers; i++, buffer++) {
-               if (!buffer->jpg.frag_tab)
-                       continue;
-
-               if (fh->buffers.need_contiguous) {
-                       frag_tab = buffer->jpg.frag_tab[0];
-
-                       if (frag_tab) {
-                               mem = bus_to_virt(le32_to_cpu(frag_tab));
-                               for (off = 0; off < zr->buffer_size; off += 
PAGE_SIZE)
-                                       ClearPageReserved(virt_to_page(mem + 
off));
-                               kfree(mem);
-                               buffer->jpg.frag_tab[0] = 0;
-                               buffer->jpg.frag_tab[1] = 0;
-                       }
-               } else {
-                       for (j = 0; j < zr->buffer_size / PAGE_SIZE; j++) {
-                               frag_tab = buffer->jpg.frag_tab[2 * j];
-
-                               if (!frag_tab)
-                                       break;
-                               
ClearPageReserved(virt_to_page(bus_to_virt(le32_to_cpu(frag_tab))));
-                               free_page((unsigned 
long)bus_to_virt(le32_to_cpu(frag_tab)));
-                               buffer->jpg.frag_tab[2 * j] = 0;
-                               buffer->jpg.frag_tab[2 * j + 1] = 0;
-                       }
-               }
-
-               free_page((unsigned long)buffer->jpg.frag_tab);
-               buffer->jpg.frag_tab = NULL;
-       }
-
-       fh->buffers.allocated = 0;
+       return result;
 }
 
 /*
@@ -431,561 +203,8 @@ static int zoran_v4l_set_format(struct zoran *zr, int 
width, int height,
        return 0;
 }
 
-static int zoran_v4l_queue_frame(struct zoran_fh *fh, int num)
-{
-       struct zoran *zr = fh->zr;
-       unsigned long flags;
-       int res = 0;
-
-       if (!fh->buffers.allocated) {
-               pci_err(zr->pci_dev, "%s - buffers not yet allocated\n", 
__func__);
-               res = -ENOMEM;
-       }
-
-       /* No grabbing outside the buffer range! */
-       if (num >= fh->buffers.num_buffers || num < 0) {
-               pci_err(zr->pci_dev, "%s - buffer %d is out of range\n", 
__func__, num);
-               res = -EINVAL;
-       }
-
-       spin_lock_irqsave(&zr->spinlock, flags);
-
-       if (fh->buffers.active == ZORAN_FREE) {
-               if (zr->v4l_buffers.active == ZORAN_FREE) {
-                       zr->v4l_buffers = fh->buffers;
-                       fh->buffers.active = ZORAN_ACTIVE;
-               } else {
-                       pci_err(zr->pci_dev, "%s - another session is already 
capturing\n", __func__);
-                       res = -EBUSY;
-               }
-       }
-
-       /* make sure a grab isn't going on currently with this buffer */
-       if (!res) {
-               switch (zr->v4l_buffers.buffer[num].state) {
-               default:
-               case BUZ_STATE_PEND:
-                       if (zr->v4l_buffers.active == ZORAN_FREE) {
-                               fh->buffers.active = ZORAN_FREE;
-                               zr->v4l_buffers.allocated = 0;
-                       }
-                       res = -EBUSY;   /* what are you doing? */
-                       break;
-               case BUZ_STATE_DONE:
-                       pci_warn(zr->pci_dev, "%s - queueing buffer %d in state 
DONE!?\n", __func__, num);
-                       /* fallthrough */
-               case BUZ_STATE_USER:
-                       /* since there is at least one unused buffer there's 
room for at least
-                        * one more pend[] entry */
-                       zr->v4l_pend[zr->v4l_pend_head++ & V4L_MASK_FRAME] = 
num;
-                       zr->v4l_buffers.buffer[num].state = BUZ_STATE_PEND;
-                       zr->v4l_buffers.buffer[num].bs.length =
-                           zr->v4l_settings.bytesperline *
-                           zr->v4l_settings.height;
-                       fh->buffers.buffer[num] = zr->v4l_buffers.buffer[num];
-                       break;
-               }
-       }
-
-       spin_unlock_irqrestore(&zr->spinlock, flags);
-
-       if (!res && zr->v4l_buffers.active == ZORAN_FREE)
-               zr->v4l_buffers.active = fh->buffers.active;
-
-       return res;
-}
-
-/*
- * Sync on a V4L buffer
- */
-
-static int v4l_sync(struct zoran_fh *fh, int frame)
-{
-       struct zoran *zr = fh->zr;
-       unsigned long flags;
-
-       if (fh->buffers.active == ZORAN_FREE) {
-               pci_err(zr->pci_dev, "%s - no grab active for this session\n", 
__func__);
-               return -EINVAL;
-       }
-
-       /* check passed-in frame number */
-       if (frame >= fh->buffers.num_buffers || frame < 0) {
-               pci_err(zr->pci_dev, "%s - frame %d is invalid\n", __func__, 
frame);
-               return -EINVAL;
-       }
-
-       /* Check if is buffer was queued at all */
-       if (zr->v4l_buffers.buffer[frame].state == BUZ_STATE_USER) {
-               pci_err(zr->pci_dev, "%s - attempt to sync on a buffer which 
was not queued?\n", __func__);
-               return -EPROTO;
-       }
-
-       mutex_unlock(&zr->lock);
-       /* wait on this buffer to get ready */
-       if (!wait_event_interruptible_timeout(zr->v4l_capq,
-               (zr->v4l_buffers.buffer[frame].state != BUZ_STATE_PEND), 10 * 
HZ)) {
-               mutex_lock(&zr->lock);
-               return -ETIME;
-       }
-       mutex_lock(&zr->lock);
-       if (signal_pending(current))
-               return -ERESTARTSYS;
-
-       /* buffer should now be in BUZ_STATE_DONE */
-       if (zr->v4l_buffers.buffer[frame].state != BUZ_STATE_DONE)
-               pci_err(zr->pci_dev, "%s - internal state error\n", __func__);
-
-       zr->v4l_buffers.buffer[frame].state = BUZ_STATE_USER;
-       fh->buffers.buffer[frame] = zr->v4l_buffers.buffer[frame];
-
-       spin_lock_irqsave(&zr->spinlock, flags);
-
-       /* Check if streaming capture has finished */
-       if (zr->v4l_pend_tail == zr->v4l_pend_head) {
-               zr36057_set_memgrab(zr, 0);
-               if (zr->v4l_buffers.active == ZORAN_ACTIVE) {
-                       fh->buffers.active = zr->v4l_buffers.active = 
ZORAN_FREE;
-                       zr->v4l_buffers.allocated = 0;
-               }
-       }
-
-       spin_unlock_irqrestore(&zr->spinlock, flags);
-
-       return 0;
-}
-
-/*
- *   Queue a MJPEG buffer for capture/playback
- */
-static int zoran_jpg_queue_frame(struct zoran_fh *fh, int num,
-                                enum zoran_codec_mode mode)
-{
-       struct zoran *zr = fh->zr;
-       unsigned long flags;
-       int res = 0;
-
-       /* Check if buffers are allocated */
-       if (!fh->buffers.allocated) {
-               pci_err(zr->pci_dev, "%s - buffers not yet allocated\n", 
__func__);
-               return -ENOMEM;
-       }
-
-       /* No grabbing outside the buffer range! */
-       if (num >= fh->buffers.num_buffers || num < 0) {
-               pci_err(zr->pci_dev, "%s - buffer %d out of range\n", __func__, 
num);
-               return -EINVAL;
-       }
-
-       /* what is the codec mode right now? */
-       if (zr->codec_mode != BUZ_MODE_IDLE && zr->codec_mode != mode) {
-               /* wrong codec mode active - invalid */
-               pci_err(zr->pci_dev, "%s - codec in wrong mode\n", __func__);
-               return -EINVAL;
-       }
-
-       if (fh->buffers.active == ZORAN_FREE) {
-               if (zr->jpg_buffers.active == ZORAN_FREE) {
-                       zr->jpg_buffers = fh->buffers;
-                       fh->buffers.active = ZORAN_ACTIVE;
-               } else {
-                       pci_err(zr->pci_dev, "%s - another session is already 
capturing\n", __func__);
-                       res = -EBUSY;
-               }
-       }
-
-       if (!res && zr->codec_mode == BUZ_MODE_IDLE) {
-               /* Ok load up the jpeg codec */
-               zr36057_enable_jpg(zr, mode);
-       }
-
-       spin_lock_irqsave(&zr->spinlock, flags);
-
-       if (!res) {
-               switch (zr->jpg_buffers.buffer[num].state) {
-               case BUZ_STATE_DONE:
-                       pci_warn(zr->pci_dev, "%s - queuing frame in 
BUZ_STATE_DONE state!?\n", __func__);
-                       /* fallthrough */
-               case BUZ_STATE_USER:
-                       /* since there is at least one unused buffer there's 
room for at
-                        *least one more pend[] entry */
-                       zr->jpg_pend[zr->jpg_que_head++ & BUZ_MASK_FRAME] = num;
-                       zr->jpg_buffers.buffer[num].state = BUZ_STATE_PEND;
-                       fh->buffers.buffer[num] = zr->jpg_buffers.buffer[num];
-                       zoran_feed_stat_com(zr);
-                       break;
-               default:
-               case BUZ_STATE_DMA:
-               case BUZ_STATE_PEND:
-                       if (zr->jpg_buffers.active == ZORAN_FREE) {
-                               fh->buffers.active = ZORAN_FREE;
-                               zr->jpg_buffers.allocated = 0;
-                       }
-                       res = -EBUSY;   /* what are you doing? */
-                       break;
-               }
-       }
-
-       spin_unlock_irqrestore(&zr->spinlock, flags);
-
-       if (!res && zr->jpg_buffers.active == ZORAN_FREE)
-               zr->jpg_buffers.active = fh->buffers.active;
-
-       return res;
-}
-
-static int jpg_qbuf(struct zoran_fh *fh, int frame, enum zoran_codec_mode mode)
-{
-       struct zoran *zr = fh->zr;
-       int res = 0;
-
-       /* Does the user want to stop streaming? */
-       if (frame < 0) {
-               if (zr->codec_mode == mode) {
-                       if (fh->buffers.active == ZORAN_FREE) {
-                               pci_err(zr->pci_dev, "%s(-1) - session not 
active\n", __func__);
-                               return -EINVAL;
-                       }
-                       fh->buffers.active = zr->jpg_buffers.active = 
ZORAN_FREE;
-                       zr->jpg_buffers.allocated = 0;
-                       zr36057_enable_jpg(zr, BUZ_MODE_IDLE);
-                       return 0;
-               } else {
-                       pci_err(zr->pci_dev, "%s - stop streaming but not in 
streaming mode\n", __func__);
-                       return -EINVAL;
-               }
-       }
-
-       res = zoran_jpg_queue_frame(fh, frame, mode);
-       if (res)
-               return res;
-
-       /* Start the jpeg codec when the first frame is queued */
-       if (!res && zr->jpg_que_head == 1)
-               jpeg_start(zr);
-
-       return res;
-}
-
-/*
- *   Sync on a MJPEG buffer
- */
-
-static int jpg_sync(struct zoran_fh *fh, struct zoran_sync *bs)
-{
-       struct zoran *zr = fh->zr;
-       unsigned long flags;
-       int frame;
-
-       if (fh->buffers.active == ZORAN_FREE) {
-               pci_err(zr->pci_dev, "%s - capture is not currently active\n", 
__func__);
-               return -EINVAL;
-       }
-       if (zr->codec_mode != BUZ_MODE_MOTION_DECOMPRESS &&
-           zr->codec_mode != BUZ_MODE_MOTION_COMPRESS) {
-               pci_err(zr->pci_dev, "%s - codec not in streaming mode\n", 
__func__);
-               return -EINVAL;
-       }
-       mutex_unlock(&zr->lock);
-       if (!wait_event_interruptible_timeout(zr->jpg_capq,
-                                             (zr->jpg_que_tail != 
zr->jpg_dma_tail ||
-                        zr->jpg_dma_tail == zr->jpg_dma_head),
-                       10 * HZ)) {
-               int isr;
-
-               btand(~ZR36057_JMC_Go_en, ZR36057_JMC);
-               udelay(1);
-               zr->codec->control(zr->codec, CODEC_G_STATUS, sizeof(isr), 
&isr);
-               mutex_lock(&zr->lock);
-               pci_err(zr->pci_dev, "%s - timeout: codec isr=0x%02x\n", 
__func__, isr);
-
-               return -ETIME;
-       }
-       mutex_lock(&zr->lock);
-       if (signal_pending(current))
-               return -ERESTARTSYS;
-
-       spin_lock_irqsave(&zr->spinlock, flags);
-
-       if (zr->jpg_dma_tail != zr->jpg_dma_head)
-               frame = zr->jpg_pend[zr->jpg_que_tail++ & BUZ_MASK_FRAME];
-       else
-               frame = zr->jpg_pend[zr->jpg_que_tail & BUZ_MASK_FRAME];
-
-       /* buffer should now be in BUZ_STATE_DONE */
-       if (zr->jpg_buffers.buffer[frame].state != BUZ_STATE_DONE)
-               pci_err(zr->pci_dev, "%s - internal state error\n", __func__);
-
-       *bs = zr->jpg_buffers.buffer[frame].bs;
-       bs->frame = frame;
-       zr->jpg_buffers.buffer[frame].state = BUZ_STATE_USER;
-       fh->buffers.buffer[frame] = zr->jpg_buffers.buffer[frame];
-
-       spin_unlock_irqrestore(&zr->spinlock, flags);
-
-       return 0;
-}
-
-static void zoran_open_init_session(struct zoran_fh *fh)
-{
-       int i;
-
-       /* Per default, map the V4L Buffers */
-       map_mode_raw(fh);
-
-       /* buffers */
-       memset(&fh->buffers, 0, sizeof(fh->buffers));
-       for (i = 0; i < MAX_FRAME; i++) {
-               fh->buffers.buffer[i].state = BUZ_STATE_USER;   /* nothing 
going on */
-               fh->buffers.buffer[i].bs.frame = i;
-       }
-       fh->buffers.allocated = 0;
-       fh->buffers.active = ZORAN_FREE;
-}
-
-static void zoran_close_end_session(struct zoran_fh *fh)
-{
-       struct zoran *zr = fh->zr;
-
-       if (fh->map_mode == ZORAN_MAP_MODE_RAW) {
-               /* v4l capture */
-               if (fh->buffers.active != ZORAN_FREE) {
-                       unsigned long flags;
-
-                       spin_lock_irqsave(&zr->spinlock, flags);
-                       zr36057_set_memgrab(zr, 0);
-                       zr->v4l_buffers.allocated = 0;
-                       zr->v4l_buffers.active = fh->buffers.active = 
ZORAN_FREE;
-                       spin_unlock_irqrestore(&zr->spinlock, flags);
-               }
-
-               /* v4l buffers */
-               if (fh->buffers.allocated)
-                       v4l_fbuffer_free(fh);
-       } else {
-               /* jpg capture */
-               if (fh->buffers.active != ZORAN_FREE) {
-                       zr36057_enable_jpg(zr, BUZ_MODE_IDLE);
-                       zr->jpg_buffers.allocated = 0;
-                       zr->jpg_buffers.active = fh->buffers.active = 
ZORAN_FREE;
-               }
-
-               /* jpg buffers */
-               if (fh->buffers.allocated)
-                       jpg_fbuffer_free(fh);
-       }
-}
-
-/*
- *   Open a zoran card. Right now the flags stuff is just playing
- */
-static int zoran_open(struct file *file)
-{
-       struct zoran *zr = video_drvdata(file);
-       struct zoran_fh *fh;
-       int res, first_open = 0;
-
-       pci_info(zr->pci_dev, "%s(%s, pid=[%d]), users(-)=%d\n", __func__, 
current->comm,
-                task_pid_nr(current), zr->user + 1);
-
-       mutex_lock(&zr->lock);
-
-       if (zr->user >= 2048) {
-               pci_err(zr->pci_dev, "too many users (%d) on device\n", 
zr->user);
-               res = -EBUSY;
-               goto fail_unlock;
-       }
-
-       /* now, create the open()-specific file_ops struct */
-       fh = kzalloc(sizeof(*fh), GFP_KERNEL);
-       if (!fh) {
-               res = -ENOMEM;
-               goto fail_unlock;
-       }
-       v4l2_fh_init(&fh->fh, video_devdata(file));
-
-       if (zr->user++ == 0)
-               first_open = 1;
-
-       /* default setup - TODO: look at flags */
-       if (first_open) {       /* First device open */
-               zr36057_restart(zr);
-               zoran_open_init_params(zr);
-               zoran_init_hardware(zr);
-
-               btor(ZR36057_ICR_IntPinEn, ZR36057_ICR);
-       }
-
-       /* set file_ops stuff */
-       file->private_data = fh;
-       fh->zr = zr;
-       zoran_open_init_session(fh);
-       v4l2_fh_add(&fh->fh);
-       mutex_unlock(&zr->lock);
-
-       return 0;
-
-fail_unlock:
-       mutex_unlock(&zr->lock);
-
-       pci_info(zr->pci_dev, "open failed (%d), users(-)=%d\n", res, zr->user);
-
-       return res;
-}
-
-static int zoran_close(struct file *file)
-{
-       struct zoran_fh *fh = file->private_data;
-       struct zoran *zr = fh->zr;
-
-       pci_info(zr->pci_dev, "%s(%s, pid=[%d]), users(+)=%d\n", __func__, 
current->comm,
-                task_pid_nr(current), zr->user - 1);
-
-       /* kernel locks (fs/device.c), so don't do that ourselves
-        * (prevents deadlocks) */
-       mutex_lock(&zr->lock);
-
-       zoran_close_end_session(fh);
-
-       if (zr->user-- == 1) {  /* Last process */
-               /* Clean up JPEG process */
-               wake_up_interruptible(&zr->jpg_capq);
-               zr36057_enable_jpg(zr, BUZ_MODE_IDLE);
-               zr->jpg_buffers.allocated = 0;
-               zr->jpg_buffers.active = ZORAN_FREE;
-
-               /* disable interrupts */
-               btand(~ZR36057_ICR_IntPinEn, ZR36057_ICR);
-
-               if (zr36067_debug > 1)
-                       print_interrupts(zr);
-
-               /* capture off */
-               wake_up_interruptible(&zr->v4l_capq);
-               zr36057_set_memgrab(zr, 0);
-               zr->v4l_buffers.allocated = 0;
-               zr->v4l_buffers.active = ZORAN_FREE;
-               zoran_set_pci_master(zr, 0);
-
-               if (!pass_through) {    /* Switch to color bar */
-                       decoder_call(zr, video, s_stream, 0);
-                       encoder_call(zr, video, s_routing, 2, 0, 0);
-               }
-       }
-       mutex_unlock(&zr->lock);
-
-       v4l2_fh_del(&fh->fh);
-       v4l2_fh_exit(&fh->fh);
-       kfree(fh);
-
-       pci_dbg(zr->pci_dev, "%s done\n", __func__);
-
-       return 0;
-}
-
-/* get the status of a buffer in the clients buffer queue */
-static int zoran_v4l2_buffer_status(struct zoran_fh *fh,
-                                   struct v4l2_buffer *buf, int num)
-{
-       struct zoran *zr = fh->zr;
-       unsigned long flags;
-
-       buf->flags = V4L2_BUF_FLAG_MAPPED | V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC;
-
-       switch (fh->map_mode) {
-       case ZORAN_MAP_MODE_RAW:
-               /* check range */
-               if (num < 0 || num >= fh->buffers.num_buffers ||
-                   !fh->buffers.allocated) {
-                       pci_err(zr->pci_dev, "%s - wrong number or buffers not 
allocated\n", __func__);
-                       return -EINVAL;
-               }
-
-               spin_lock_irqsave(&zr->spinlock, flags);
-               pci_dbg(zr->pci_dev, "%s() - raw active=%c, buffer %d: 
state=%c, map=%c\n", __func__,
-                       "FAL"[fh->buffers.active], num,
-                       "UPMD"[zr->v4l_buffers.buffer[num].state],
-                       fh->buffers.buffer[num].map ? 'Y' : 'N');
-               spin_unlock_irqrestore(&zr->spinlock, flags);
-
-               buf->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
-               buf->length = zr->buffer_size;
-
-               /* get buffer */
-               buf->bytesused = fh->buffers.buffer[num].bs.length;
-               if (fh->buffers.buffer[num].state == BUZ_STATE_DONE ||
-                   fh->buffers.buffer[num].state == BUZ_STATE_USER) {
-                       buf->sequence = fh->buffers.buffer[num].bs.seq;
-                       buf->flags |= V4L2_BUF_FLAG_DONE;
-                       v4l2_buffer_set_timestamp(buf, 
fh->buffers.buffer[num].bs.ts);
-               } else {
-                       buf->flags |= V4L2_BUF_FLAG_QUEUED;
-               }
-
-               if (zr->v4l_settings.height <= BUZ_MAX_HEIGHT / 2)
-                       buf->field = V4L2_FIELD_TOP;
-               else
-                       buf->field = V4L2_FIELD_INTERLACED;
-
-               break;
-
-       case ZORAN_MAP_MODE_JPG_REC:
-       case ZORAN_MAP_MODE_JPG_PLAY:
-
-               /* check range */
-               if (num < 0 || num >= fh->buffers.num_buffers ||
-                   !fh->buffers.allocated) {
-                       pci_err(zr->pci_dev, "%s - wrong number or buffers not 
allocated\n", __func__);
-                       return -EINVAL;
-               }
-
-               buf->type = (fh->map_mode == ZORAN_MAP_MODE_JPG_REC) ?
-                             V4L2_BUF_TYPE_VIDEO_CAPTURE :
-                             V4L2_BUF_TYPE_VIDEO_OUTPUT;
-               buf->length = zr->buffer_size;
-
-               /* these variables are only written after frame has been 
captured */
-               if (fh->buffers.buffer[num].state == BUZ_STATE_DONE ||
-                   fh->buffers.buffer[num].state == BUZ_STATE_USER) {
-                       buf->sequence = fh->buffers.buffer[num].bs.seq;
-                       v4l2_buffer_set_timestamp(buf, 
fh->buffers.buffer[num].bs.ts);
-                       buf->bytesused = fh->buffers.buffer[num].bs.length;
-                       buf->flags |= V4L2_BUF_FLAG_DONE;
-               } else {
-                       buf->flags |= V4L2_BUF_FLAG_QUEUED;
-               }
-
-               /* which fields are these? */
-               if (zr->jpg_settings.TmpDcm != 1)
-                       buf->field = zr->jpg_settings.odd_even ?
-                               V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM;
-               else
-                       buf->field = zr->jpg_settings.odd_even ?
-                               V4L2_FIELD_SEQ_TB : V4L2_FIELD_SEQ_BT;
-
-               break;
-
-       default:
-
-               pci_err(zr->pci_dev, "%s - invalid buffer type|map_mode 
(%d|%d)\n",
-                      __func__, buf->type, fh->map_mode);
-               return -EINVAL;
-       }
-
-       buf->memory = V4L2_MEMORY_MMAP;
-       buf->index = num;
-       buf->m.offset = buf->length * num;
-
-       return 0;
-}
-
 static int zoran_set_norm(struct zoran *zr, v4l2_std_id norm)
 {
-       if (zr->v4l_buffers.active != ZORAN_FREE ||
-           zr->jpg_buffers.active != ZORAN_FREE) {
-               pr_warn("%s: %s called while in playback/capture mode\n", 
ZR_DEVNAME(zr), __func__);
-               return -EBUSY;
-       }
 
        if (!(norm & zr->card.norms)) {
                pci_err(zr->pci_dev, "%s - unsupported norm %llx\n", __func__, 
norm);
@@ -1013,12 +232,6 @@ static int zoran_set_input(struct zoran *zr, int input)
        if (input == zr->input)
                return 0;
 
-       if (zr->v4l_buffers.active != ZORAN_FREE ||
-           zr->jpg_buffers.active != ZORAN_FREE) {
-               pci_warn(zr->pci_dev, "%s called while in playback/capture 
mode\n", __func__);
-               return -EBUSY;
-       }
-
        if (input < 0 || input >= zr->card.inputs) {
                pci_err(zr->pci_dev, "%s - unsupported input %d\n", __func__, 
input);
                return -EINVAL;
@@ -1119,12 +332,10 @@ static int zoran_g_fmt_vid_out(struct file *file, void 
*__fh,
 static int zoran_g_fmt_vid_cap(struct file *file, void *__fh,
                               struct v4l2_format *fmt)
 {
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
-
-       if (fh->map_mode != ZORAN_MAP_MODE_RAW)
-               return zoran_g_fmt_vid_out(file, fh, fmt);
+       struct zoran *zr = video_drvdata(file);
 
+       if (zr->map_mode != ZORAN_MAP_MODE_RAW)
+               return zoran_g_fmt_vid_out(file, __fh, fmt);
        fmt->fmt.pix.width = zr->v4l_settings.width;
        fmt->fmt.pix.height = zr->v4l_settings.height;
        fmt->fmt.pix.sizeimage = zr->buffer_size;
@@ -1205,13 +416,12 @@ static int zoran_try_fmt_vid_out(struct file *file, void 
*__fh,
 static int zoran_try_fmt_vid_cap(struct file *file, void *__fh,
                                 struct v4l2_format *fmt)
 {
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
+       struct zoran *zr = video_drvdata(file);
        int bpp;
        int i;
 
        if (fmt->fmt.pix.pixelformat == V4L2_PIX_FMT_MJPEG)
-               return zoran_try_fmt_vid_out(file, fh, fmt);
+               return zoran_try_fmt_vid_out(file, __fh, fmt);
 
        for (i = 0; i < NUM_FORMATS; i++)
                if (zoran_formats[i].fourcc == fmt->fmt.pix.pixelformat)
@@ -1238,8 +448,7 @@ static int zoran_try_fmt_vid_cap(struct file *file, void 
*__fh,
 static int zoran_s_fmt_vid_out(struct file *file, void *__fh,
                               struct v4l2_format *fmt)
 {
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
+       struct zoran *zr = video_drvdata(file);
        __le32 printformat = __cpu_to_le32(fmt->fmt.pix.pixelformat);
        struct zoran_jpg_settings settings;
        int res = 0;
@@ -1251,12 +460,6 @@ static int zoran_s_fmt_vid_out(struct file *file, void 
*__fh,
        if (fmt->fmt.pix.pixelformat != V4L2_PIX_FMT_MJPEG)
                return -EINVAL;
 
-       if (fh->buffers.allocated) {
-               pci_err(zr->pci_dev, "VIDIOC_S_FMT - cannot change capture 
mode\n");
-               res = -EBUSY;
-               return res;
-       }
-
        if (!fmt->fmt.pix.height || !fmt->fmt.pix.width)
                return -EINVAL;
 
@@ -1299,7 +502,11 @@ static int zoran_s_fmt_vid_out(struct file *file, void 
*__fh,
        /* it's ok, so set them */
        zr->jpg_settings = settings;
 
-       map_mode_jpg(fh, fmt->type == V4L2_BUF_TYPE_VIDEO_OUTPUT);
+       if (fmt->type == V4L2_BUF_TYPE_VIDEO_OUTPUT)
+               zr->map_mode = ZORAN_MAP_MODE_JPG_REC;
+       else
+               zr->map_mode = ZORAN_MAP_MODE_JPG_PLAY;
+
        zr->buffer_size = zoran_v4l2_calc_bufsize(&zr->jpg_settings);
 
        /* tell the user what we actually did */
@@ -1339,13 +546,6 @@ static int zoran_s_fmt_vid_cap(struct file *file, void 
*__fh,
                return -EINVAL;
        }
 
-       if ((fh->map_mode != ZORAN_MAP_MODE_RAW && fh->buffers.allocated) ||
-           fh->buffers.active != ZORAN_FREE) {
-               pci_err(zr->pci_dev, "VIDIOC_S_FMT - cannot change capture 
mode\n");
-               res = -EBUSY;
-               return res;
-       }
-
        fmt->fmt.pix.pixelformat = zoran_formats[i].fourcc;
        if (fmt->fmt.pix.height > BUZ_MAX_HEIGHT)
                fmt->fmt.pix.height = BUZ_MAX_HEIGHT;
@@ -1356,7 +556,7 @@ static int zoran_s_fmt_vid_cap(struct file *file, void 
*__fh,
        if (fmt->fmt.pix.width < BUZ_MIN_WIDTH)
                fmt->fmt.pix.width = BUZ_MIN_WIDTH;
 
-       map_mode_raw(fh);
+       zr->map_mode = ZORAN_MAP_MODE_RAW;
 
        res = zoran_v4l_set_format(zr, fmt->fmt.pix.width, fmt->fmt.pix.height,
                                   &zoran_formats[i]);
@@ -1374,309 +574,6 @@ static int zoran_s_fmt_vid_cap(struct file *file, void 
*__fh,
        return res;
 }
 
-static int zoran_streamoff(struct file *file, void *__fh, enum v4l2_buf_type 
type);
-
-static int zoran_reqbufs(struct file *file, void *__fh, struct 
v4l2_requestbuffers *req)
-{
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
-       int res = 0;
-
-       if (req->memory != V4L2_MEMORY_MMAP) {
-               pci_err(zr->pci_dev, "only MEMORY_MMAP capture is supported, 
not %d\n", req->memory);
-               return -EINVAL;
-       }
-
-       if (req->count == 0)
-               return zoran_streamoff(file, fh, req->type);
-
-       if (fh->buffers.allocated) {
-               pr_warn("%s: VIDIOC_REQBUFS - buffers already allocated\n", 
ZR_DEVNAME(zr));
-               res = -EBUSY;
-               return res;
-       }
-
-       if (fh->map_mode == ZORAN_MAP_MODE_RAW &&
-           req->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) {
-               /* control user input */
-               if (req->count < 2)
-                       req->count = 2;
-               if (req->count > v4l_nbufs)
-                       req->count = v4l_nbufs;
-
-               /* The next mmap will map the V4L buffers */
-               map_mode_raw(fh);
-               fh->buffers.num_buffers = req->count;
-
-               if (v4l_fbuffer_alloc(fh)) {
-                       res = -ENOMEM;
-                       return res;
-               }
-       } else if (fh->map_mode == ZORAN_MAP_MODE_JPG_REC ||
-                  fh->map_mode == ZORAN_MAP_MODE_JPG_PLAY) {
-               /* we need to calculate size ourselves now */
-               if (req->count < 4)
-                       req->count = 4;
-               if (req->count > jpg_nbufs)
-                       req->count = jpg_nbufs;
-
-               /* The next mmap will map the MJPEG buffers */
-               map_mode_jpg(fh, req->type == V4L2_BUF_TYPE_VIDEO_OUTPUT);
-               fh->buffers.num_buffers = req->count;
-               zr->buffer_size = zoran_v4l2_calc_bufsize(&zr->jpg_settings);
-
-               if (jpg_fbuffer_alloc(fh)) {
-                       res = -ENOMEM;
-                       return res;
-               }
-       } else {
-               pci_err(zr->pci_dev, "VIDIOC_REQBUFS - unknown type %d\n", 
req->type);
-               res = -EINVAL;
-               return res;
-       }
-       return res;
-}
-
-static int zoran_querybuf(struct file *file, void *__fh, struct v4l2_buffer 
*buf)
-{
-       struct zoran_fh *fh = __fh;
-
-       return zoran_v4l2_buffer_status(fh, buf, buf->index);
-}
-
-static int zoran_qbuf(struct file *file, void *__fh, struct v4l2_buffer *buf)
-{
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
-       int res = 0, codec_mode, buf_type;
-
-       switch (fh->map_mode) {
-       case ZORAN_MAP_MODE_RAW:
-               if (buf->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) {
-                       pci_err(zr->pci_dev, "VIDIOC_QBUF - invalid 
buf->type=%d for map_mode=%d\n",
-                               buf->type, fh->map_mode);
-                       res = -EINVAL;
-                       return res;
-               }
-
-               res = zoran_v4l_queue_frame(fh, buf->index);
-               if (res)
-                       return res;
-               if (!zr->v4l_memgrab_active && fh->buffers.active == 
ZORAN_LOCKED)
-                       zr36057_set_memgrab(zr, 1);
-               break;
-
-       case ZORAN_MAP_MODE_JPG_REC:
-       case ZORAN_MAP_MODE_JPG_PLAY:
-               if (fh->map_mode == ZORAN_MAP_MODE_JPG_PLAY) {
-                       buf_type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
-                       codec_mode = BUZ_MODE_MOTION_DECOMPRESS;
-               } else {
-                       buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
-                       codec_mode = BUZ_MODE_MOTION_COMPRESS;
-               }
-
-               if (buf->type != buf_type) {
-                       pci_err(zr->pci_dev, "VIDIOC_QBUF - invalid 
buf->type=%d for map_mode=%d\n",
-                               buf->type, fh->map_mode);
-                       res = -EINVAL;
-                       return res;
-               }
-
-               res = zoran_jpg_queue_frame(fh, buf->index, codec_mode);
-               if (res != 0)
-                       return res;
-               if (zr->codec_mode == BUZ_MODE_IDLE &&
-                   fh->buffers.active == ZORAN_LOCKED)
-                       zr36057_enable_jpg(zr, codec_mode);
-
-               break;
-
-       default:
-               pci_err(zr->pci_dev, "VIDIOC_QBUF - unsupported type %d\n", 
buf->type);
-               res = -EINVAL;
-               break;
-       }
-       return res;
-}
-
-static int zoran_dqbuf(struct file *file, void *__fh, struct v4l2_buffer *buf)
-{
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
-       int res = 0, buf_type, num = -1;        /* compiler borks here (?) */
-
-       switch (fh->map_mode) {
-       case ZORAN_MAP_MODE_RAW:
-               if (buf->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) {
-                       pci_err(zr->pci_dev, "VIDIOC_QBUF - invalid 
buf->type=%d for map_mode=%d\n",
-                               buf->type, fh->map_mode);
-                       res = -EINVAL;
-                       return res;
-               }
-
-               num = zr->v4l_pend[zr->v4l_sync_tail & V4L_MASK_FRAME];
-               if (file->f_flags & O_NONBLOCK &&
-                   zr->v4l_buffers.buffer[num].state != BUZ_STATE_DONE) {
-                       res = -EAGAIN;
-                       return res;
-               }
-               res = v4l_sync(fh, num);
-               if (res)
-                       return res;
-               zr->v4l_sync_tail++;
-               res = zoran_v4l2_buffer_status(fh, buf, num);
-               break;
-
-       case ZORAN_MAP_MODE_JPG_REC:
-       case ZORAN_MAP_MODE_JPG_PLAY:
-       {
-               struct zoran_sync bs;
-
-               if (fh->map_mode == ZORAN_MAP_MODE_JPG_PLAY)
-                       buf_type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
-               else
-                       buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
-
-               if (buf->type != buf_type) {
-                       pci_err(zr->pci_dev, "VIDIOC_QBUF - invalid 
buf->type=%d for map_mode=%d\n",
-                               buf->type, fh->map_mode);
-                       res = -EINVAL;
-                       return res;
-               }
-
-               num = zr->jpg_pend[zr->jpg_que_tail & BUZ_MASK_FRAME];
-
-               if (file->f_flags & O_NONBLOCK &&
-                   zr->jpg_buffers.buffer[num].state != BUZ_STATE_DONE) {
-                       res = -EAGAIN;
-                       return res;
-               }
-               bs.frame = 0; /* suppress compiler warning */
-               res = jpg_sync(fh, &bs);
-               if (res)
-                       return res;
-               res = zoran_v4l2_buffer_status(fh, buf, bs.frame);
-               break;
-       }
-
-       default:
-               pci_err(zr->pci_dev, "VIDIOC_DQBUF - unsupported type %d\n", 
buf->type);
-               res = -EINVAL;
-               break;
-       }
-       return res;
-}
-
-static int zoran_streamon(struct file *file, void *__fh, enum v4l2_buf_type 
type)
-{
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
-       int res = 0;
-
-       switch (fh->map_mode) {
-       case ZORAN_MAP_MODE_RAW:        /* raw capture */
-               if (zr->v4l_buffers.active != ZORAN_ACTIVE ||
-                   fh->buffers.active != ZORAN_ACTIVE) {
-                       res = -EBUSY;
-                       return res;
-               }
-
-               zr->v4l_buffers.active = fh->buffers.active = ZORAN_LOCKED;
-
-               zr->v4l_sync_tail = zr->v4l_pend_tail;
-               if (!zr->v4l_memgrab_active &&
-                   zr->v4l_pend_head != zr->v4l_pend_tail) {
-                       zr36057_set_memgrab(zr, 1);
-               }
-               break;
-
-       case ZORAN_MAP_MODE_JPG_REC:
-       case ZORAN_MAP_MODE_JPG_PLAY:
-               /* what is the codec mode right now? */
-               if (zr->jpg_buffers.active != ZORAN_ACTIVE ||
-                   fh->buffers.active != ZORAN_ACTIVE) {
-                       res = -EBUSY;
-                       return res;
-               }
-
-               zr->jpg_buffers.active = fh->buffers.active = ZORAN_LOCKED;
-
-               if (zr->jpg_que_head != zr->jpg_que_tail) {
-                       /* Start the jpeg codec when the first frame is queued 
*/
-                       jpeg_start(zr);
-               }
-               break;
-
-       default:
-               pci_err(zr->pci_dev, "VIDIOC_STREAMON - invalid map mode %d\n", 
fh->map_mode);
-               res = -EINVAL;
-               break;
-       }
-       return res;
-}
-
-static int zoran_streamoff(struct file *file, void *__fh, enum v4l2_buf_type 
type)
-{
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
-       int i, res = 0;
-       unsigned long flags;
-
-       switch (fh->map_mode) {
-       case ZORAN_MAP_MODE_RAW:        /* raw capture */
-               if (fh->buffers.active == ZORAN_FREE &&
-                   zr->v4l_buffers.active != ZORAN_FREE) {
-                       res = -EPERM;   /* stay off other's settings! */
-                       return res;
-               }
-               if (zr->v4l_buffers.active == ZORAN_FREE)
-                       return res;
-
-               spin_lock_irqsave(&zr->spinlock, flags);
-               /* unload capture */
-               if (zr->v4l_memgrab_active)
-                       zr36057_set_memgrab(zr, 0);
-
-               for (i = 0; i < fh->buffers.num_buffers; i++)
-                       zr->v4l_buffers.buffer[i].state = BUZ_STATE_USER;
-               fh->buffers = zr->v4l_buffers;
-
-               zr->v4l_buffers.active = fh->buffers.active = ZORAN_FREE;
-
-               zr->v4l_grab_seq = 0;
-               zr->v4l_pend_head = zr->v4l_pend_tail = 0;
-               zr->v4l_sync_tail = 0;
-
-               spin_unlock_irqrestore(&zr->spinlock, flags);
-
-               break;
-
-       case ZORAN_MAP_MODE_JPG_REC:
-       case ZORAN_MAP_MODE_JPG_PLAY:
-               if (fh->buffers.active == ZORAN_FREE &&
-                   zr->jpg_buffers.active != ZORAN_FREE) {
-                       res = -EPERM;   /* stay off other's settings! */
-                       return res;
-               }
-               if (zr->jpg_buffers.active == ZORAN_FREE)
-                       return res;
-
-               res = jpg_qbuf(fh, -1,
-                              (fh->map_mode == ZORAN_MAP_MODE_JPG_REC) ?
-                            BUZ_MODE_MOTION_COMPRESS :
-                            BUZ_MODE_MOTION_DECOMPRESS);
-               if (res)
-                       return res;
-               break;
-       default:
-               pci_err(zr->pci_dev, "VIDIOC_STREAMOFF - invalid map mode 
%d\n", fh->map_mode);
-               res = -EINVAL;
-               break;
-       }
-       return res;
-}
-
 static int zoran_g_std(struct file *file, void *__fh, v4l2_std_id *std)
 {
        struct zoran *zr = video_drvdata(file);
@@ -1690,11 +587,10 @@ static int zoran_s_std(struct file *file, void *__fh, 
v4l2_std_id std)
        struct zoran *zr = video_drvdata(file);
        int res = 0;
 
-       res = zoran_set_norm(zr, std);
-       if (res)
-               return res;
+       if (zr->running != ZORAN_MAP_MODE_NONE)
+               return -EBUSY;
 
-       res = wait_grab_pending(zr);
+       res = zoran_set_norm(zr, std);
        return res;
 }
 
@@ -1729,12 +625,10 @@ static int zoran_s_input(struct file *file, void *__fh, 
unsigned int input)
        struct zoran *zr = video_drvdata(file);
        int res;
 
-       res = zoran_set_input(zr, input);
-       if (res)
-               return res;
+       if (zr->running != ZORAN_MAP_MODE_NONE)
+               return -EBUSY;
 
-       /* Make sure the changes come into effect */
-       res = wait_grab_pending(zr);
+       res = zoran_set_input(zr, input);
        return res;
 }
 
@@ -1746,11 +640,12 @@ static int zoran_enum_output(struct file *file, void 
*__fh,
 
        outp->index = 0;
        outp->type = V4L2_OUTPUT_TYPE_ANALOGVGAOVERLAY;
+       outp->std = V4L2_STD_NTSC | V4L2_STD_PAL | V4L2_STD_SECAM;
+       outp->capabilities = V4L2_OUT_CAP_STD;
        strscpy(outp->name, "Autodetect", sizeof(outp->name));
 
        return 0;
 }
-
 static int zoran_g_output(struct file *file, void *__fh, unsigned int *output)
 {
        *output = 0;
@@ -1765,19 +660,14 @@ static int zoran_s_output(struct file *file, void *__fh, 
unsigned int output)
 
        return 0;
 }
-
 /* cropping (sub-frame capture) */
 static int zoran_g_selection(struct file *file, void *__fh, struct 
v4l2_selection *sel)
 {
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
+       struct zoran *zr = video_drvdata(file);
 
        if (sel->type != V4L2_BUF_TYPE_VIDEO_OUTPUT &&
-           sel->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
-               return -EINVAL;
-
-       if (fh->map_mode == ZORAN_MAP_MODE_RAW) {
-               pci_err(zr->pci_dev, "VIDIOC_G_SELECTION - subcapture only 
supported for compressed capture\n");
+           sel->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) {
+               pci_err(zr->pci_dev, "%s invalid combinaison\n", __func__);
                return -EINVAL;
        }
 
@@ -1806,8 +696,7 @@ static int zoran_g_selection(struct file *file, void 
*__fh, struct v4l2_selectio
 
 static int zoran_s_selection(struct file *file, void *__fh, struct 
v4l2_selection *sel)
 {
-       struct zoran_fh *fh = __fh;
-       struct zoran *zr = fh->zr;
+       struct zoran *zr = video_drvdata(file);
        struct zoran_jpg_settings settings;
        int res;
 
@@ -1821,18 +710,13 @@ static int zoran_s_selection(struct file *file, void 
*__fh, struct v4l2_selectio
        if (sel->target != V4L2_SEL_TGT_CROP)
                return -EINVAL;
 
-       if (fh->map_mode == ZORAN_MAP_MODE_RAW) {
+       if (zr->map_mode == ZORAN_MAP_MODE_RAW) {
                pci_err(zr->pci_dev, "VIDIOC_S_SELECTION - subcapture only 
supported for compressed capture\n");
                return -EINVAL;
        }
 
        settings = zr->jpg_settings;
 
-       if (fh->buffers.allocated) {
-               pci_err(zr->pci_dev, "VIDIOC_S_SELECTION - cannot change 
settings while active\n");
-               return -EBUSY;
-       }
-
        /* move into a form that we understand */
        settings.img_x = sel->r.left;
        settings.img_y = sel->r.top;
@@ -1849,260 +733,6 @@ static int zoran_s_selection(struct file *file, void 
*__fh, struct v4l2_selectio
        return res;
 }
 
-static __poll_t zoran_poll(struct file *file, poll_table  *wait)
-{
-       struct zoran_fh *fh = file->private_data;
-       struct zoran *zr = fh->zr;
-       __poll_t res = v4l2_ctrl_poll(file, wait);
-       int frame;
-       unsigned long flags;
-
-       /* we should check whether buffers are ready to be synced on
-        * (w/o waits - O_NONBLOCK) here
-        * if ready for read (sync), return EPOLLIN|EPOLLRDNORM,
-        * if ready for write (sync), return EPOLLOUT|EPOLLWRNORM,
-        * if error, return EPOLLERR,
-        * if no buffers queued or so, return EPOLLNVAL
-        */
-
-       switch (fh->map_mode) {
-       case ZORAN_MAP_MODE_RAW:
-               poll_wait(file, &zr->v4l_capq, wait);
-               frame = zr->v4l_pend[zr->v4l_sync_tail & V4L_MASK_FRAME];
-
-               spin_lock_irqsave(&zr->spinlock, flags);
-               pci_dbg(zr->pci_dev, "%s() raw - active=%c, sync_tail=%lu/%c, 
pend_tail=%lu, pend_head=%lu\n",
-                       __func__,
-                       "FAL"[fh->buffers.active], zr->v4l_sync_tail,
-                       "UPMD"[zr->v4l_buffers.buffer[frame].state],
-                       zr->v4l_pend_tail, zr->v4l_pend_head);
-               /* Process is the one capturing? */
-               if (fh->buffers.active != ZORAN_FREE &&
-                   /* Buffer ready to DQBUF? */
-                   zr->v4l_buffers.buffer[frame].state == BUZ_STATE_DONE)
-                       res |= EPOLLIN | EPOLLRDNORM;
-               spin_unlock_irqrestore(&zr->spinlock, flags);
-
-               break;
-
-       case ZORAN_MAP_MODE_JPG_REC:
-       case ZORAN_MAP_MODE_JPG_PLAY:
-               poll_wait(file, &zr->jpg_capq, wait);
-               frame = zr->jpg_pend[zr->jpg_que_tail & BUZ_MASK_FRAME];
-
-               spin_lock_irqsave(&zr->spinlock, flags);
-               pci_dbg(zr->pci_dev, "%s() jpg - active=%c, que_tail=%lu/%c, 
que_head=%lu, dma=%lu/%lu\n",
-                       __func__,
-                       "FAL"[fh->buffers.active], zr->jpg_que_tail,
-                       "UPMD"[zr->jpg_buffers.buffer[frame].state],
-                       zr->jpg_que_head, zr->jpg_dma_tail, zr->jpg_dma_head);
-               if (fh->buffers.active != ZORAN_FREE &&
-                   zr->jpg_buffers.buffer[frame].state == BUZ_STATE_DONE) {
-                       if (fh->map_mode == ZORAN_MAP_MODE_JPG_REC)
-                               res |= EPOLLIN | EPOLLRDNORM;
-                       else
-                               res |= EPOLLOUT | EPOLLWRNORM;
-               }
-               spin_unlock_irqrestore(&zr->spinlock, flags);
-
-               break;
-
-       default:
-               pci_err(zr->pci_dev, "%s - internal error, unknown 
map_mode=%d\n", __func__, fh->map_mode);
-               res |= EPOLLERR;
-       }
-
-       return res;
-}
-
-/*
- * This maps the buffers to user space.
- *
- * Depending on the state of fh->map_mode
- * the V4L or the MJPEG buffers are mapped
- * per buffer or all together
- *
- * Note that we need to connect to some
- * unmap signal event to unmap the de-allocate
- * the buffer accordingly (zoran_vm_close())
- */
-
-static void zoran_vm_open(struct vm_area_struct *vma)
-{
-       struct zoran_mapping *map = vma->vm_private_data;
-
-       atomic_inc(&map->count);
-}
-
-static void zoran_vm_close(struct vm_area_struct *vma)
-{
-       struct zoran_mapping *map = vma->vm_private_data;
-       struct zoran_fh *fh = map->fh;
-       struct zoran *zr = fh->zr;
-       int i;
-
-       pci_info(zr->pci_dev, "%s - munmap(%s)\n", ZR_DEVNAME(zr), 
mode_name(fh->map_mode));
-
-       for (i = 0; i < fh->buffers.num_buffers; i++) {
-               if (fh->buffers.buffer[i].map == map)
-                       fh->buffers.buffer[i].map = NULL;
-       }
-       kfree(map);
-
-       /* Any buffers still mapped? */
-       for (i = 0; i < fh->buffers.num_buffers; i++) {
-               if (fh->buffers.buffer[i].map)
-                       return;
-       }
-
-       pci_info(zr->pci_dev, "%s - free %s buffers\n", __func__, 
mode_name(fh->map_mode));
-
-       if (fh->map_mode == ZORAN_MAP_MODE_RAW) {
-               if (fh->buffers.active != ZORAN_FREE) {
-                       unsigned long flags;
-
-                       spin_lock_irqsave(&zr->spinlock, flags);
-                       zr36057_set_memgrab(zr, 0);
-                       zr->v4l_buffers.allocated = 0;
-                       zr->v4l_buffers.active = fh->buffers.active = 
ZORAN_FREE;
-                       spin_unlock_irqrestore(&zr->spinlock, flags);
-               }
-               v4l_fbuffer_free(fh);
-       } else {
-               if (fh->buffers.active != ZORAN_FREE) {
-                       jpg_qbuf(fh, -1, zr->codec_mode);
-                       zr->jpg_buffers.allocated = 0;
-                       zr->jpg_buffers.active = fh->buffers.active = 
ZORAN_FREE;
-               }
-               jpg_fbuffer_free(fh);
-       }
-}
-
-static const struct vm_operations_struct zoran_vm_ops = {
-       .open = zoran_vm_open,
-       .close = zoran_vm_close,
-};
-
-static int zoran_mmap(struct file *file, struct vm_area_struct *vma)
-{
-       struct zoran_fh *fh = file->private_data;
-       struct zoran *zr = fh->zr;
-       unsigned long size = (vma->vm_end - vma->vm_start);
-       unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;
-       int i, j;
-       unsigned long page, start = vma->vm_start, todo, pos, fraglen;
-       int first, last;
-       struct zoran_mapping *map;
-       int res = 0;
-
-       pci_info(zr->pci_dev, "%s(%s) of 0x%08lx-0x%08lx (size=%lu)\n", 
__func__,
-                mode_name(fh->map_mode), vma->vm_start, vma->vm_end, size);
-
-       if (!(vma->vm_flags & VM_SHARED) || !(vma->vm_flags & VM_READ) ||
-           !(vma->vm_flags & VM_WRITE)) {
-               pci_err(zr->pci_dev, "%s - no MAP_SHARED/PROT_{READ,WRITE} 
given\n", __func__);
-               return -EINVAL;
-       }
-
-       if (!fh->buffers.allocated) {
-               pci_err(zr->pci_dev, "%s(%s) - buffers not yet allocated\n", 
__func__, mode_name(fh->map_mode));
-               res = -ENOMEM;
-               return res;
-       }
-
-       first = offset / zr->buffer_size;
-       last = first - 1 + size / zr->buffer_size;
-       if (offset % zr->buffer_size != 0 ||
-           size % zr->buffer_size != 0 || first < 0 ||
-           last < 0 || first >= fh->buffers.num_buffers ||
-           last >= zr->buffer_size) {
-               pci_err(zr->pci_dev, "%s(%s) - offset=%lu or size=%lu invalid 
for bufsize=%d and numbufs=%d\n",
-                       __func__, mode_name(fh->map_mode), offset, size,
-                       zr->buffer_size,
-                       fh->buffers.num_buffers);
-               res = -EINVAL;
-               return res;
-       }
-
-       /* Check if any buffers are already mapped */
-       for (i = first; i <= last; i++) {
-               if (fh->buffers.buffer[i].map) {
-                       pci_err(zr->pci_dev, "%s(%s) - buffer %d already 
mapped\n", __func__, mode_name(fh->map_mode), i);
-                       res = -EBUSY;
-                       return res;
-               }
-       }
-
-       /* map these buffers */
-       map = kmalloc(sizeof(*map), GFP_KERNEL);
-       if (!map) {
-               res = -ENOMEM;
-               return res;
-       }
-       map->fh = fh;
-       atomic_set(&map->count, 1);
-
-       vma->vm_ops = &zoran_vm_ops;
-       vma->vm_flags |= VM_DONTEXPAND;
-       vma->vm_private_data = map;
-
-       if (fh->map_mode == ZORAN_MAP_MODE_RAW) {
-               for (i = first; i <= last; i++) {
-                       todo = size;
-                       if (todo > zr->buffer_size)
-                               todo = zr->buffer_size;
-                       page = fh->buffers.buffer[i].v4l.fbuffer_phys;
-                       if (remap_pfn_range(vma, start, page >> PAGE_SHIFT,
-                                           todo, PAGE_SHARED)) {
-                               pci_err(zr->pci_dev, "%s(V4L) - remap_pfn_range 
failed\n", __func__);
-                               res = -EAGAIN;
-                               return res;
-                       }
-                       size -= todo;
-                       start += todo;
-                       fh->buffers.buffer[i].map = map;
-                       if (size == 0)
-                               break;
-               }
-       } else {
-               for (i = first; i <= last; i++) {
-                       for (j = 0;
-                            j < zr->buffer_size / PAGE_SIZE;
-                            j++) {
-                               fraglen =
-                                   (le32_to_cpu(fh->buffers.buffer[i].jpg.
-                                    frag_tab[2 * j + 1]) & ~1) << 1;
-                               todo = size;
-                               if (todo > fraglen)
-                                       todo = fraglen;
-                               pos =
-                                   le32_to_cpu(fh->buffers.
-                                   buffer[i].jpg.frag_tab[2 * j]);
-                               /* should just be pos on i386 */
-                               page = virt_to_phys(bus_to_virt(pos))
-                                                               >> PAGE_SHIFT;
-                               if (remap_pfn_range(vma, start, page,
-                                                   todo, PAGE_SHARED)) {
-                                       pci_err(zr->pci_dev, "%s(V4L) - 
remap_pfn_range failed\n", __func__);
-                                       res = -EAGAIN;
-                                       return res;
-                               }
-                               size -= todo;
-                               start += todo;
-                               if (size == 0)
-                                       break;
-                               if (le32_to_cpu(fh->buffers.buffer[i].jpg.
-                                   frag_tab[2 * j + 1]) & 1)
-                                       break;  /* was last fragment */
-                       }
-                       fh->buffers.buffer[i].map = map;
-                       if (size == 0)
-                               break;
-               }
-       }
-       return res;
-}
-
 static int zoran_g_parm(struct file *file, void *priv, struct v4l2_streamparm 
*parm)
 {
        if (parm->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
@@ -2129,12 +759,14 @@ static const struct v4l2_ioctl_ops zoran_ioctl_ops = {
        .vidioc_s_output                    = zoran_s_output,*/
        .vidioc_g_std                       = zoran_g_std,
        .vidioc_s_std                       = zoran_s_std,
-       .vidioc_reqbufs                     = zoran_reqbufs,
-       .vidioc_querybuf                    = zoran_querybuf,
-       .vidioc_qbuf                        = zoran_qbuf,
-       .vidioc_dqbuf                       = zoran_dqbuf,
-       .vidioc_streamon                    = zoran_streamon,
-       .vidioc_streamoff                   = zoran_streamoff,
+       .vidioc_create_bufs                 = vb2_ioctl_create_bufs,
+       .vidioc_reqbufs                     = vb2_ioctl_reqbufs,
+       .vidioc_querybuf                    = vb2_ioctl_querybuf,
+       .vidioc_qbuf                        = vb2_ioctl_qbuf,
+       .vidioc_dqbuf                       = vb2_ioctl_dqbuf,
+       .vidioc_expbuf                      = vb2_ioctl_expbuf,
+       .vidioc_streamon                    = vb2_ioctl_streamon,
+       .vidioc_streamoff                   = vb2_ioctl_streamoff,
        .vidioc_enum_fmt_vid_cap            = zoran_enum_fmt_vid_cap,
 /*     .vidioc_enum_fmt_vid_out            = zoran_enum_fmt_vid_out,*/
        .vidioc_g_fmt_vid_cap               = zoran_g_fmt_vid_cap,
@@ -2149,11 +781,13 @@ static const struct v4l2_ioctl_ops zoran_ioctl_ops = {
 
 static const struct v4l2_file_operations zoran_fops = {
        .owner = THIS_MODULE,
-       .open = zoran_open,
-       .release = zoran_close,
        .unlocked_ioctl = video_ioctl2,
-       .mmap = zoran_mmap,
-       .poll = zoran_poll,
+       .open           = v4l2_fh_open,
+       .release        = vb2_fop_release,
+       .read           = vb2_fop_read,
+       .write          = vb2_fop_write,
+       .mmap           = vb2_fop_mmap,
+       .poll           = vb2_fop_poll,
 };
 
 const struct video_device zoran_template = {
@@ -2177,11 +811,13 @@ static int zr_vb2_queue_setup(struct vb2_queue *vq, 
unsigned int *nbuffers, unsi
        if (*nbuffers < vq->min_buffers_needed)
                *nbuffers = vq->min_buffers_needed;
 
-       if (*nplanes)
+       if (*nplanes) {
                if (sizes[0] < size)
                        return -EINVAL;
                else
                        return 0;
+       }
+
        *nplanes = 1;
        sizes[0] = size;
 
@@ -2207,7 +843,10 @@ static int zr_vb2_prepare(struct vb2_buffer *vb)
 {
        struct zoran *zr = vb2_get_drv_priv(vb->vb2_queue);
 
+       if (vb2_plane_size(vb, 0) < zr->buffer_size)
+               return -EINVAL;
        zr->prepared++;
+
        return 0;
 }
 
-- 
2.26.2

Reply via email to