linux/drivers/media/video/cx23885/cx23885-video.c
<<
>>
Prefs
   1/*
   2 *  Driver for the Conexant CX23885 PCIe bridge
   3 *
   4 *  Copyright (c) 2007 Steven Toth <stoth@linuxtv.org>
   5 *
   6 *  This program is free software; you can redistribute it and/or modify
   7 *  it under the terms of the GNU General Public License as published by
   8 *  the Free Software Foundation; either version 2 of the License, or
   9 *  (at your option) any later version.
  10 *
  11 *  This program is distributed in the hope that it will be useful,
  12 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  13 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14 *
  15 *  GNU General Public License for more details.
  16 *
  17 *  You should have received a copy of the GNU General Public License
  18 *  along with this program; if not, write to the Free Software
  19 *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  20 */
  21
  22#include <linux/init.h>
  23#include <linux/list.h>
  24#include <linux/module.h>
  25#include <linux/moduleparam.h>
  26#include <linux/kmod.h>
  27#include <linux/kernel.h>
  28#include <linux/slab.h>
  29#include <linux/smp_lock.h>
  30#include <linux/interrupt.h>
  31#include <linux/delay.h>
  32#include <linux/kthread.h>
  33#include <asm/div64.h>
  34
  35#include "cx23885.h"
  36#include <media/v4l2-common.h>
  37#include <media/v4l2-ioctl.h>
  38
  39MODULE_DESCRIPTION("v4l2 driver module for cx23885 based TV cards");
  40MODULE_AUTHOR("Steven Toth <stoth@linuxtv.org>");
  41MODULE_LICENSE("GPL");
  42
  43/* ------------------------------------------------------------------ */
  44
  45static unsigned int video_nr[] = {[0 ... (CX23885_MAXBOARDS - 1)] = UNSET };
  46static unsigned int vbi_nr[]   = {[0 ... (CX23885_MAXBOARDS - 1)] = UNSET };
  47static unsigned int radio_nr[] = {[0 ... (CX23885_MAXBOARDS - 1)] = UNSET };
  48
  49module_param_array(video_nr, int, NULL, 0444);
  50module_param_array(vbi_nr,   int, NULL, 0444);
  51module_param_array(radio_nr, int, NULL, 0444);
  52
  53MODULE_PARM_DESC(video_nr, "video device numbers");
  54MODULE_PARM_DESC(vbi_nr, "vbi device numbers");
  55MODULE_PARM_DESC(radio_nr, "radio device numbers");
  56
  57static unsigned int video_debug;
  58module_param(video_debug, int, 0644);
  59MODULE_PARM_DESC(video_debug, "enable debug messages [video]");
  60
  61static unsigned int irq_debug;
  62module_param(irq_debug, int, 0644);
  63MODULE_PARM_DESC(irq_debug, "enable debug messages [IRQ handler]");
  64
  65static unsigned int vid_limit = 16;
  66module_param(vid_limit, int, 0644);
  67MODULE_PARM_DESC(vid_limit, "capture memory limit in megabytes");
  68
  69#define dprintk(level, fmt, arg...)\
  70        do { if (video_debug >= level)\
  71                printk(KERN_DEBUG "%s/0: " fmt, dev->name, ## arg);\
  72        } while (0)
  73
  74/* ------------------------------------------------------------------- */
  75/* static data                                                         */
  76
  77#define FORMAT_FLAGS_PACKED       0x01
  78
  79static struct cx23885_fmt formats[] = {
  80        {
  81                .name     = "8 bpp, gray",
  82                .fourcc   = V4L2_PIX_FMT_GREY,
  83                .depth    = 8,
  84                .flags    = FORMAT_FLAGS_PACKED,
  85        }, {
  86                .name     = "15 bpp RGB, le",
  87                .fourcc   = V4L2_PIX_FMT_RGB555,
  88                .depth    = 16,
  89                .flags    = FORMAT_FLAGS_PACKED,
  90        }, {
  91                .name     = "15 bpp RGB, be",
  92                .fourcc   = V4L2_PIX_FMT_RGB555X,
  93                .depth    = 16,
  94                .flags    = FORMAT_FLAGS_PACKED,
  95        }, {
  96                .name     = "16 bpp RGB, le",
  97                .fourcc   = V4L2_PIX_FMT_RGB565,
  98                .depth    = 16,
  99                .flags    = FORMAT_FLAGS_PACKED,
 100        }, {
 101                .name     = "16 bpp RGB, be",
 102                .fourcc   = V4L2_PIX_FMT_RGB565X,
 103                .depth    = 16,
 104                .flags    = FORMAT_FLAGS_PACKED,
 105        }, {
 106                .name     = "24 bpp RGB, le",
 107                .fourcc   = V4L2_PIX_FMT_BGR24,
 108                .depth    = 24,
 109                .flags    = FORMAT_FLAGS_PACKED,
 110        }, {
 111                .name     = "32 bpp RGB, le",
 112                .fourcc   = V4L2_PIX_FMT_BGR32,
 113                .depth    = 32,
 114                .flags    = FORMAT_FLAGS_PACKED,
 115        }, {
 116                .name     = "32 bpp RGB, be",
 117                .fourcc   = V4L2_PIX_FMT_RGB32,
 118                .depth    = 32,
 119                .flags    = FORMAT_FLAGS_PACKED,
 120        }, {
 121                .name     = "4:2:2, packed, YUYV",
 122                .fourcc   = V4L2_PIX_FMT_YUYV,
 123                .depth    = 16,
 124                .flags    = FORMAT_FLAGS_PACKED,
 125        }, {
 126                .name     = "4:2:2, packed, UYVY",
 127                .fourcc   = V4L2_PIX_FMT_UYVY,
 128                .depth    = 16,
 129                .flags    = FORMAT_FLAGS_PACKED,
 130        },
 131};
 132
 133static struct cx23885_fmt *format_by_fourcc(unsigned int fourcc)
 134{
 135        unsigned int i;
 136
 137        for (i = 0; i < ARRAY_SIZE(formats); i++)
 138                if (formats[i].fourcc == fourcc)
 139                        return formats+i;
 140
 141        printk(KERN_ERR "%s(0x%08x) NOT FOUND\n", __func__, fourcc);
 142        return NULL;
 143}
 144
 145/* ------------------------------------------------------------------- */
 146
 147static const struct v4l2_queryctrl no_ctl = {
 148        .name  = "42",
 149        .flags = V4L2_CTRL_FLAG_DISABLED,
 150};
 151
 152static struct cx23885_ctrl cx23885_ctls[] = {
 153        /* --- video --- */
 154        {
 155                .v = {
 156                        .id            = V4L2_CID_BRIGHTNESS,
 157                        .name          = "Brightness",
 158                        .minimum       = 0x00,
 159                        .maximum       = 0xff,
 160                        .step          = 1,
 161                        .default_value = 0x7f,
 162                        .type          = V4L2_CTRL_TYPE_INTEGER,
 163                },
 164                .off                   = 128,
 165                .reg                   = LUMA_CTRL,
 166                .mask                  = 0x00ff,
 167                .shift                 = 0,
 168        }, {
 169                .v = {
 170                        .id            = V4L2_CID_CONTRAST,
 171                        .name          = "Contrast",
 172                        .minimum       = 0,
 173                        .maximum       = 0xff,
 174                        .step          = 1,
 175                        .default_value = 0x3f,
 176                        .type          = V4L2_CTRL_TYPE_INTEGER,
 177                },
 178                .off                   = 0,
 179                .reg                   = LUMA_CTRL,
 180                .mask                  = 0xff00,
 181                .shift                 = 8,
 182        }, {
 183                .v = {
 184                        .id            = V4L2_CID_HUE,
 185                        .name          = "Hue",
 186                        .minimum       = 0,
 187                        .maximum       = 0xff,
 188                        .step          = 1,
 189                        .default_value = 0x7f,
 190                        .type          = V4L2_CTRL_TYPE_INTEGER,
 191                },
 192                .off                   = 128,
 193                .reg                   = CHROMA_CTRL,
 194                .mask                  = 0xff0000,
 195                .shift                 = 16,
 196        }, {
 197                /* strictly, this only describes only U saturation.
 198                 * V saturation is handled specially through code.
 199                 */
 200                .v = {
 201                        .id            = V4L2_CID_SATURATION,
 202                        .name          = "Saturation",
 203                        .minimum       = 0,
 204                        .maximum       = 0xff,
 205                        .step          = 1,
 206                        .default_value = 0x7f,
 207                        .type          = V4L2_CTRL_TYPE_INTEGER,
 208                },
 209                .off                   = 0,
 210                .reg                   = CHROMA_CTRL,
 211                .mask                  = 0x00ff,
 212                .shift                 = 0,
 213        }, {
 214        /* --- audio --- */
 215                .v = {
 216                        .id            = V4L2_CID_AUDIO_MUTE,
 217                        .name          = "Mute",
 218                        .minimum       = 0,
 219                        .maximum       = 1,
 220                        .default_value = 1,
 221                        .type          = V4L2_CTRL_TYPE_BOOLEAN,
 222                },
 223                .reg                   = PATH1_CTL1,
 224                .mask                  = (0x1f << 24),
 225                .shift                 = 24,
 226        }, {
 227                .v = {
 228                        .id            = V4L2_CID_AUDIO_VOLUME,
 229                        .name          = "Volume",
 230                        .minimum       = 0,
 231                        .maximum       = 0x3f,
 232                        .step          = 1,
 233                        .default_value = 0x3f,
 234                        .type          = V4L2_CTRL_TYPE_INTEGER,
 235                },
 236                .reg                   = PATH1_VOL_CTL,
 237                .mask                  = 0xff,
 238                .shift                 = 0,
 239        }
 240};
 241static const int CX23885_CTLS = ARRAY_SIZE(cx23885_ctls);
 242
 243/* Must be sorted from low to high control ID! */
 244static const u32 cx23885_user_ctrls[] = {
 245        V4L2_CID_USER_CLASS,
 246        V4L2_CID_BRIGHTNESS,
 247        V4L2_CID_CONTRAST,
 248        V4L2_CID_SATURATION,
 249        V4L2_CID_HUE,
 250        V4L2_CID_AUDIO_VOLUME,
 251        V4L2_CID_AUDIO_MUTE,
 252        0
 253};
 254
 255static const u32 *ctrl_classes[] = {
 256        cx23885_user_ctrls,
 257        NULL
 258};
 259
 260static void cx23885_video_wakeup(struct cx23885_dev *dev,
 261                 struct cx23885_dmaqueue *q, u32 count)
 262{
 263        struct cx23885_buffer *buf;
 264        int bc;
 265
 266        for (bc = 0;; bc++) {
 267                if (list_empty(&q->active))
 268                        break;
 269                buf = list_entry(q->active.next,
 270                                 struct cx23885_buffer, vb.queue);
 271
 272                /* count comes from the hw and is is 16bit wide --
 273                 * this trick handles wrap-arounds correctly for
 274                 * up to 32767 buffers in flight... */
 275                if ((s16) (count - buf->count) < 0)
 276                        break;
 277
 278                do_gettimeofday(&buf->vb.ts);
 279                dprintk(2, "[%p/%d] wakeup reg=%d buf=%d\n", buf, buf->vb.i,
 280                        count, buf->count);
 281                buf->vb.state = VIDEOBUF_DONE;
 282                list_del(&buf->vb.queue);
 283                wake_up(&buf->vb.done);
 284        }
 285        if (list_empty(&q->active))
 286                del_timer(&q->timeout);
 287        else
 288                mod_timer(&q->timeout, jiffies+BUFFER_TIMEOUT);
 289        if (bc != 1)
 290                printk(KERN_ERR "%s: %d buffers handled (should be 1)\n",
 291                        __func__, bc);
 292}
 293
 294static int cx23885_set_tvnorm(struct cx23885_dev *dev, v4l2_std_id norm)
 295{
 296        dprintk(1, "%s(norm = 0x%08x) name: [%s]\n",
 297                __func__,
 298                (unsigned int)norm,
 299                v4l2_norm_to_name(norm));
 300
 301        dev->tvnorm = norm;
 302
 303        call_all(dev, core, s_std, norm);
 304
 305        return 0;
 306}
 307
 308static struct video_device *cx23885_vdev_init(struct cx23885_dev *dev,
 309                                    struct pci_dev *pci,
 310                                    struct video_device *template,
 311                                    char *type)
 312{
 313        struct video_device *vfd;
 314        dprintk(1, "%s()\n", __func__);
 315
 316        vfd = video_device_alloc();
 317        if (NULL == vfd)
 318                return NULL;
 319        *vfd = *template;
 320        vfd->minor = -1;
 321        vfd->v4l2_dev = &dev->v4l2_dev;
 322        vfd->release = video_device_release;
 323        snprintf(vfd->name, sizeof(vfd->name), "%s %s (%s)",
 324                 dev->name, type, cx23885_boards[dev->board].name);
 325        return vfd;
 326}
 327
 328static int cx23885_ctrl_query(struct v4l2_queryctrl *qctrl)
 329{
 330        int i;
 331
 332        if (qctrl->id < V4L2_CID_BASE ||
 333            qctrl->id >= V4L2_CID_LASTP1)
 334                return -EINVAL;
 335        for (i = 0; i < CX23885_CTLS; i++)
 336                if (cx23885_ctls[i].v.id == qctrl->id)
 337                        break;
 338        if (i == CX23885_CTLS) {
 339                *qctrl = no_ctl;
 340                return 0;
 341        }
 342        *qctrl = cx23885_ctls[i].v;
 343        return 0;
 344}
 345
 346/* ------------------------------------------------------------------- */
 347/* resource management                                                 */
 348
 349static int res_get(struct cx23885_dev *dev, struct cx23885_fh *fh,
 350        unsigned int bit)
 351{
 352        dprintk(1, "%s()\n", __func__);
 353        if (fh->resources & bit)
 354                /* have it already allocated */
 355                return 1;
 356
 357        /* is it free? */
 358        mutex_lock(&dev->lock);
 359        if (dev->resources & bit) {
 360                /* no, someone else uses it */
 361                mutex_unlock(&dev->lock);
 362                return 0;
 363        }
 364        /* it's free, grab it */
 365        fh->resources  |= bit;
 366        dev->resources |= bit;
 367        dprintk(1, "res: get %d\n", bit);
 368        mutex_unlock(&dev->lock);
 369        return 1;
 370}
 371
 372static int res_check(struct cx23885_fh *fh, unsigned int bit)
 373{
 374        return fh->resources & bit;
 375}
 376
 377static int res_locked(struct cx23885_dev *dev, unsigned int bit)
 378{
 379        return dev->resources & bit;
 380}
 381
 382static void res_free(struct cx23885_dev *dev, struct cx23885_fh *fh,
 383        unsigned int bits)
 384{
 385        BUG_ON((fh->resources & bits) != bits);
 386        dprintk(1, "%s()\n", __func__);
 387
 388        mutex_lock(&dev->lock);
 389        fh->resources  &= ~bits;
 390        dev->resources &= ~bits;
 391        dprintk(1, "res: put %d\n", bits);
 392        mutex_unlock(&dev->lock);
 393}
 394
 395static int cx23885_video_mux(struct cx23885_dev *dev, unsigned int input)
 396{
 397        dprintk(1, "%s() video_mux: %d [vmux=%d, gpio=0x%x,0x%x,0x%x,0x%x]\n",
 398                __func__,
 399                input, INPUT(input)->vmux,
 400                INPUT(input)->gpio0, INPUT(input)->gpio1,
 401                INPUT(input)->gpio2, INPUT(input)->gpio3);
 402        dev->input = input;
 403
 404        /* Tell the internal A/V decoder */
 405        v4l2_subdev_call(dev->sd_cx25840, video, s_routing,
 406                        INPUT(input)->vmux, 0, 0);
 407
 408        return 0;
 409}
 410
 411/* ------------------------------------------------------------------ */
 412static int cx23885_set_scale(struct cx23885_dev *dev, unsigned int width,
 413        unsigned int height, enum v4l2_field field)
 414{
 415        dprintk(1, "%s()\n", __func__);
 416        return 0;
 417}
 418
 419static int cx23885_start_video_dma(struct cx23885_dev *dev,
 420                           struct cx23885_dmaqueue *q,
 421                           struct cx23885_buffer *buf)
 422{
 423        dprintk(1, "%s()\n", __func__);
 424
 425        /* setup fifo + format */
 426        cx23885_sram_channel_setup(dev, &dev->sram_channels[SRAM_CH01],
 427                                buf->bpl, buf->risc.dma);
 428        cx23885_set_scale(dev, buf->vb.width, buf->vb.height, buf->vb.field);
 429
 430        /* reset counter */
 431        cx_write(VID_A_GPCNT_CTL, 3);
 432        q->count = 1;
 433
 434        /* enable irq */
 435        cx_set(PCI_INT_MSK, cx_read(PCI_INT_MSK) | 0x01);
 436        cx_set(VID_A_INT_MSK, 0x000011);
 437
 438        /* start dma */
 439        cx_set(DEV_CNTRL2, (1<<5));
 440        cx_set(VID_A_DMA_CTL, 0x11); /* FIFO and RISC enable */
 441
 442        return 0;
 443}
 444
 445
 446static int cx23885_restart_video_queue(struct cx23885_dev *dev,
 447                               struct cx23885_dmaqueue *q)
 448{
 449        struct cx23885_buffer *buf, *prev;
 450        struct list_head *item;
 451        dprintk(1, "%s()\n", __func__);
 452
 453        if (!list_empty(&q->active)) {
 454                buf = list_entry(q->active.next, struct cx23885_buffer,
 455                        vb.queue);
 456                dprintk(2, "restart_queue [%p/%d]: restart dma\n",
 457                        buf, buf->vb.i);
 458                cx23885_start_video_dma(dev, q, buf);
 459                list_for_each(item, &q->active) {
 460                        buf = list_entry(item, struct cx23885_buffer,
 461                                vb.queue);
 462                        buf->count    = q->count++;
 463                }
 464                mod_timer(&q->timeout, jiffies+BUFFER_TIMEOUT);
 465                return 0;
 466        }
 467
 468        prev = NULL;
 469        for (;;) {
 470                if (list_empty(&q->queued))
 471                        return 0;
 472                buf = list_entry(q->queued.next, struct cx23885_buffer,
 473                        vb.queue);
 474                if (NULL == prev) {
 475                        list_move_tail(&buf->vb.queue, &q->active);
 476                        cx23885_start_video_dma(dev, q, buf);
 477                        buf->vb.state = VIDEOBUF_ACTIVE;
 478                        buf->count    = q->count++;
 479                        mod_timer(&q->timeout, jiffies+BUFFER_TIMEOUT);
 480                        dprintk(2, "[%p/%d] restart_queue - first active\n",
 481                                buf, buf->vb.i);
 482
 483                } else if (prev->vb.width  == buf->vb.width  &&
 484                           prev->vb.height == buf->vb.height &&
 485                           prev->fmt       == buf->fmt) {
 486                        list_move_tail(&buf->vb.queue, &q->active);
 487                        buf->vb.state = VIDEOBUF_ACTIVE;
 488                        buf->count    = q->count++;
 489                        prev->risc.jmp[1] = cpu_to_le32(buf->risc.dma);
 490                        prev->risc.jmp[2] = cpu_to_le32(0); /* Bits 63 - 32 */
 491                        dprintk(2, "[%p/%d] restart_queue - move to active\n",
 492                                buf, buf->vb.i);
 493                } else {
 494                        return 0;
 495                }
 496                prev = buf;
 497        }
 498}
 499
 500static int buffer_setup(struct videobuf_queue *q, unsigned int *count,
 501        unsigned int *size)
 502{
 503        struct cx23885_fh *fh = q->priv_data;
 504
 505        *size = fh->fmt->depth*fh->width*fh->height >> 3;
 506        if (0 == *count)
 507                *count = 32;
 508        while (*size * *count > vid_limit * 1024 * 1024)
 509                (*count)--;
 510        return 0;
 511}
 512
 513static int buffer_prepare(struct videobuf_queue *q, struct videobuf_buffer *vb,
 514               enum v4l2_field field)
 515{
 516        struct cx23885_fh *fh  = q->priv_data;
 517        struct cx23885_dev *dev = fh->dev;
 518        struct cx23885_buffer *buf =
 519                container_of(vb, struct cx23885_buffer, vb);
 520        int rc, init_buffer = 0;
 521        u32 line0_offset, line1_offset;
 522        struct videobuf_dmabuf *dma = videobuf_to_dma(&buf->vb);
 523
 524        BUG_ON(NULL == fh->fmt);
 525        if (fh->width  < 48 || fh->width  > norm_maxw(dev->tvnorm) ||
 526            fh->height < 32 || fh->height > norm_maxh(dev->tvnorm))
 527                return -EINVAL;
 528        buf->vb.size = (fh->width * fh->height * fh->fmt->depth) >> 3;
 529        if (0 != buf->vb.baddr  &&  buf->vb.bsize < buf->vb.size)
 530                return -EINVAL;
 531
 532        if (buf->fmt       != fh->fmt    ||
 533            buf->vb.width  != fh->width  ||
 534            buf->vb.height != fh->height ||
 535            buf->vb.field  != field) {
 536                buf->fmt       = fh->fmt;
 537                buf->vb.width  = fh->width;
 538                buf->vb.height = fh->height;
 539                buf->vb.field  = field;
 540                init_buffer = 1;
 541        }
 542
 543        if (VIDEOBUF_NEEDS_INIT == buf->vb.state) {
 544                init_buffer = 1;
 545                rc = videobuf_iolock(q, &buf->vb, NULL);
 546                if (0 != rc)
 547                        goto fail;
 548        }
 549
 550        if (init_buffer) {
 551                buf->bpl = buf->vb.width * buf->fmt->depth >> 3;
 552                switch (buf->vb.field) {
 553                case V4L2_FIELD_TOP:
 554                        cx23885_risc_buffer(dev->pci, &buf->risc,
 555                                         dma->sglist, 0, UNSET,
 556                                         buf->bpl, 0, buf->vb.height);
 557                        break;
 558                case V4L2_FIELD_BOTTOM:
 559                        cx23885_risc_buffer(dev->pci, &buf->risc,
 560                                         dma->sglist, UNSET, 0,
 561                                         buf->bpl, 0, buf->vb.height);
 562                        break;
 563                case V4L2_FIELD_INTERLACED:
 564                        if (dev->tvnorm & V4L2_STD_NTSC) {
 565                                /* cx25840 transmits NTSC bottom field first */
 566                                dprintk(1, "%s() Creating NTSC risc\n",
 567                                        __func__);
 568                                line0_offset = buf->bpl;
 569                                line1_offset = 0;
 570                        } else {
 571                                /* All other formats are top field first */
 572                                dprintk(1, "%s() Creating PAL/SECAM risc\n",
 573                                        __func__);
 574                                line0_offset = 0;
 575                                line1_offset = buf->bpl;
 576                        }
 577                        cx23885_risc_buffer(dev->pci, &buf->risc,
 578                                        dma->sglist, line0_offset,
 579                                        line1_offset,
 580                                        buf->bpl, buf->bpl,
 581                                        buf->vb.height >> 1);
 582                        break;
 583                case V4L2_FIELD_SEQ_TB:
 584                        cx23885_risc_buffer(dev->pci, &buf->risc,
 585                                         dma->sglist,
 586                                         0, buf->bpl * (buf->vb.height >> 1),
 587                                         buf->bpl, 0,
 588                                         buf->vb.height >> 1);
 589                        break;
 590                case V4L2_FIELD_SEQ_BT:
 591                        cx23885_risc_buffer(dev->pci, &buf->risc,
 592                                         dma->sglist,
 593                                         buf->bpl * (buf->vb.height >> 1), 0,
 594                                         buf->bpl, 0,
 595                                         buf->vb.height >> 1);
 596                        break;
 597                default:
 598                        BUG();
 599                }
 600        }
 601        dprintk(2, "[%p/%d] buffer_prep - %dx%d %dbpp \"%s\" - dma=0x%08lx\n",
 602                buf, buf->vb.i,
 603                fh->width, fh->height, fh->fmt->depth, fh->fmt->name,
 604                (unsigned long)buf->risc.dma);
 605
 606        buf->vb.state = VIDEOBUF_PREPARED;
 607        return 0;
 608
 609 fail:
 610        cx23885_free_buffer(q, buf);
 611        return rc;
 612}
 613
 614static void buffer_queue(struct videobuf_queue *vq, struct videobuf_buffer *vb)
 615{
 616        struct cx23885_buffer   *buf = container_of(vb,
 617                struct cx23885_buffer, vb);
 618        struct cx23885_buffer   *prev;
 619        struct cx23885_fh       *fh   = vq->priv_data;
 620        struct cx23885_dev      *dev  = fh->dev;
 621        struct cx23885_dmaqueue *q    = &dev->vidq;
 622
 623        /* add jump to stopper */
 624        buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | RISC_CNT_INC);
 625        buf->risc.jmp[1] = cpu_to_le32(q->stopper.dma);
 626        buf->risc.jmp[2] = cpu_to_le32(0); /* bits 63-32 */
 627
 628        if (!list_empty(&q->queued)) {
 629                list_add_tail(&buf->vb.queue, &q->queued);
 630                buf->vb.state = VIDEOBUF_QUEUED;
 631                dprintk(2, "[%p/%d] buffer_queue - append to queued\n",
 632                        buf, buf->vb.i);
 633
 634        } else if (list_empty(&q->active)) {
 635                list_add_tail(&buf->vb.queue, &q->active);
 636                cx23885_start_video_dma(dev, q, buf);
 637                buf->vb.state = VIDEOBUF_ACTIVE;
 638                buf->count    = q->count++;
 639                mod_timer(&q->timeout, jiffies+BUFFER_TIMEOUT);
 640                dprintk(2, "[%p/%d] buffer_queue - first active\n",
 641                        buf, buf->vb.i);
 642
 643        } else {
 644                prev = list_entry(q->active.prev, struct cx23885_buffer,
 645                        vb.queue);
 646                if (prev->vb.width  == buf->vb.width  &&
 647                    prev->vb.height == buf->vb.height &&
 648                    prev->fmt       == buf->fmt) {
 649                        list_add_tail(&buf->vb.queue, &q->active);
 650                        buf->vb.state = VIDEOBUF_ACTIVE;
 651                        buf->count    = q->count++;
 652                        prev->risc.jmp[1] = cpu_to_le32(buf->risc.dma);
 653                        /* 64 bit bits 63-32 */
 654                        prev->risc.jmp[2] = cpu_to_le32(0);
 655                        dprintk(2, "[%p/%d] buffer_queue - append to active\n",
 656                                buf, buf->vb.i);
 657
 658                } else {
 659                        list_add_tail(&buf->vb.queue, &q->queued);
 660                        buf->vb.state = VIDEOBUF_QUEUED;
 661                        dprintk(2, "[%p/%d] buffer_queue - first queued\n",
 662                                buf, buf->vb.i);
 663                }
 664        }
 665}
 666
 667static void buffer_release(struct videobuf_queue *q,
 668        struct videobuf_buffer *vb)
 669{
 670        struct cx23885_buffer *buf = container_of(vb,
 671                struct cx23885_buffer, vb);
 672
 673        cx23885_free_buffer(q, buf);
 674}
 675
 676static struct videobuf_queue_ops cx23885_video_qops = {
 677        .buf_setup    = buffer_setup,
 678        .buf_prepare  = buffer_prepare,
 679        .buf_queue    = buffer_queue,
 680        .buf_release  = buffer_release,
 681};
 682
 683static struct videobuf_queue *get_queue(struct cx23885_fh *fh)
 684{
 685        switch (fh->type) {
 686        case V4L2_BUF_TYPE_VIDEO_CAPTURE:
 687                return &fh->vidq;
 688        case V4L2_BUF_TYPE_VBI_CAPTURE:
 689                return &fh->vbiq;
 690        default:
 691                BUG();
 692                return NULL;
 693        }
 694}
 695
 696static int get_resource(struct cx23885_fh *fh)
 697{
 698        switch (fh->type) {
 699        case V4L2_BUF_TYPE_VIDEO_CAPTURE:
 700                return RESOURCE_VIDEO;
 701        case V4L2_BUF_TYPE_VBI_CAPTURE:
 702                return RESOURCE_VBI;
 703        default:
 704                BUG();
 705                return 0;
 706        }
 707}
 708
 709static int video_open(struct file *file)
 710{
 711        int minor = video_devdata(file)->minor;
 712        struct cx23885_dev *h, *dev = NULL;
 713        struct cx23885_fh *fh;
 714        struct list_head *list;
 715        enum v4l2_buf_type type = 0;
 716        int radio = 0;
 717
 718        lock_kernel();
 719        list_for_each(list, &cx23885_devlist) {
 720                h = list_entry(list, struct cx23885_dev, devlist);
 721                if (h->video_dev &&
 722                    h->video_dev->minor == minor) {
 723                        dev  = h;
 724                        type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
 725                }
 726                if (h->vbi_dev &&
 727                    h->vbi_dev->minor == minor) {
 728                        dev  = h;
 729                        type = V4L2_BUF_TYPE_VBI_CAPTURE;
 730                }
 731                if (h->radio_dev &&
 732                    h->radio_dev->minor == minor) {
 733                        radio = 1;
 734                        dev   = h;
 735                }
 736        }
 737        if (NULL == dev) {
 738                unlock_kernel();
 739                return -ENODEV;
 740        }
 741
 742        dprintk(1, "open minor=%d radio=%d type=%s\n",
 743                minor, radio, v4l2_type_names[type]);
 744
 745        /* allocate + initialize per filehandle data */
 746        fh = kzalloc(sizeof(*fh), GFP_KERNEL);
 747        if (NULL == fh) {
 748                unlock_kernel();
 749                return -ENOMEM;
 750        }
 751        file->private_data = fh;
 752        fh->dev      = dev;
 753        fh->radio    = radio;
 754        fh->type     = type;
 755        fh->width    = 320;
 756        fh->height   = 240;
 757        fh->fmt      = format_by_fourcc(V4L2_PIX_FMT_BGR24);
 758
 759        videobuf_queue_sg_init(&fh->vidq, &cx23885_video_qops,
 760                            &dev->pci->dev, &dev->slock,
 761                            V4L2_BUF_TYPE_VIDEO_CAPTURE,
 762                            V4L2_FIELD_INTERLACED,
 763                            sizeof(struct cx23885_buffer),
 764                            fh);
 765
 766        dprintk(1, "post videobuf_queue_init()\n");
 767
 768        unlock_kernel();
 769
 770        return 0;
 771}
 772
 773static ssize_t video_read(struct file *file, char __user *data,
 774        size_t count, loff_t *ppos)
 775{
 776        struct cx23885_fh *fh = file->private_data;
 777
 778        switch (fh->type) {
 779        case V4L2_BUF_TYPE_VIDEO_CAPTURE:
 780                if (res_locked(fh->dev, RESOURCE_VIDEO))
 781                        return -EBUSY;
 782                return videobuf_read_one(&fh->vidq, data, count, ppos,
 783                                         file->f_flags & O_NONBLOCK);
 784        case V4L2_BUF_TYPE_VBI_CAPTURE:
 785                if (!res_get(fh->dev, fh, RESOURCE_VBI))
 786                        return -EBUSY;
 787                return videobuf_read_stream(&fh->vbiq, data, count, ppos, 1,
 788                                            file->f_flags & O_NONBLOCK);
 789        default:
 790                BUG();
 791                return 0;
 792        }
 793}
 794
 795static unsigned int video_poll(struct file *file,
 796        struct poll_table_struct *wait)
 797{
 798        struct cx23885_fh *fh = file->private_data;
 799        struct cx23885_buffer *buf;
 800        unsigned int rc = POLLERR;
 801
 802        if (V4L2_BUF_TYPE_VBI_CAPTURE == fh->type) {
 803                if (!res_get(fh->dev, fh, RESOURCE_VBI))
 804                        return POLLERR;
 805                return videobuf_poll_stream(file, &fh->vbiq, wait);
 806        }
 807
 808        mutex_lock(&fh->vidq.vb_lock);
 809        if (res_check(fh, RESOURCE_VIDEO)) {
 810                /* streaming capture */
 811                if (list_empty(&fh->vidq.stream))
 812                        goto done;
 813                buf = list_entry(fh->vidq.stream.next,
 814                        struct cx23885_buffer, vb.stream);
 815        } else {
 816                /* read() capture */
 817                buf = (struct cx23885_buffer *)fh->vidq.read_buf;
 818                if (NULL == buf)
 819                        goto done;
 820        }
 821        poll_wait(file, &buf->vb.done, wait);
 822        if (buf->vb.state == VIDEOBUF_DONE ||
 823            buf->vb.state == VIDEOBUF_ERROR)
 824                rc =  POLLIN|POLLRDNORM;
 825        else
 826                rc = 0;
 827done:
 828        mutex_unlock(&fh->vidq.vb_lock);
 829        return rc;
 830}
 831
 832static int video_release(struct file *file)
 833{
 834        struct cx23885_fh *fh = file->private_data;
 835        struct cx23885_dev *dev = fh->dev;
 836
 837        /* turn off overlay */
 838        if (res_check(fh, RESOURCE_OVERLAY)) {
 839                /* FIXME */
 840                res_free(dev, fh, RESOURCE_OVERLAY);
 841        }
 842
 843        /* stop video capture */
 844        if (res_check(fh, RESOURCE_VIDEO)) {
 845                videobuf_queue_cancel(&fh->vidq);
 846                res_free(dev, fh, RESOURCE_VIDEO);
 847        }
 848        if (fh->vidq.read_buf) {
 849                buffer_release(&fh->vidq, fh->vidq.read_buf);
 850                kfree(fh->vidq.read_buf);
 851        }
 852
 853        /* stop vbi capture */
 854        if (res_check(fh, RESOURCE_VBI)) {
 855                if (fh->vbiq.streaming)
 856                        videobuf_streamoff(&fh->vbiq);
 857                if (fh->vbiq.reading)
 858                        videobuf_read_stop(&fh->vbiq);
 859                res_free(dev, fh, RESOURCE_VBI);
 860        }
 861
 862        videobuf_mmap_free(&fh->vidq);
 863        file->private_data = NULL;
 864        kfree(fh);
 865
 866        /* We are not putting the tuner to sleep here on exit, because
 867         * we want to use the mpeg encoder in another session to capture
 868         * tuner video. Closing this will result in no video to the encoder.
 869         */
 870
 871        return 0;
 872}
 873
 874static int video_mmap(struct file *file, struct vm_area_struct *vma)
 875{
 876        struct cx23885_fh *fh = file->private_data;
 877
 878        return videobuf_mmap_mapper(get_queue(fh), vma);
 879}
 880
 881/* ------------------------------------------------------------------ */
 882/* VIDEO CTRL IOCTLS                                                  */
 883
 884static int cx23885_get_control(struct cx23885_dev *dev,
 885        struct v4l2_control *ctl)
 886{
 887        dprintk(1, "%s() calling cx25840(VIDIOC_G_CTRL)\n", __func__);
 888        call_all(dev, core, g_ctrl, ctl);
 889        return 0;
 890}
 891
 892static int cx23885_set_control(struct cx23885_dev *dev,
 893        struct v4l2_control *ctl)
 894{
 895        dprintk(1, "%s() calling cx25840(VIDIOC_S_CTRL)"
 896                " (disabled - no action)\n", __func__);
 897        return 0;
 898}
 899
 900static void init_controls(struct cx23885_dev *dev)
 901{
 902        struct v4l2_control ctrl;
 903        int i;
 904
 905        for (i = 0; i < CX23885_CTLS; i++) {
 906                ctrl.id = cx23885_ctls[i].v.id;
 907                ctrl.value = cx23885_ctls[i].v.default_value;
 908
 909                cx23885_set_control(dev, &ctrl);
 910        }
 911}
 912
 913/* ------------------------------------------------------------------ */
 914/* VIDEO IOCTLS                                                       */
 915
 916static int vidioc_g_fmt_vid_cap(struct file *file, void *priv,
 917        struct v4l2_format *f)
 918{
 919        struct cx23885_fh *fh   = priv;
 920
 921        f->fmt.pix.width        = fh->width;
 922        f->fmt.pix.height       = fh->height;
 923        f->fmt.pix.field        = fh->vidq.field;
 924        f->fmt.pix.pixelformat  = fh->fmt->fourcc;
 925        f->fmt.pix.bytesperline =
 926                (f->fmt.pix.width * fh->fmt->depth) >> 3;
 927        f->fmt.pix.sizeimage =
 928                f->fmt.pix.height * f->fmt.pix.bytesperline;
 929
 930        return 0;
 931}
 932
 933static int vidioc_try_fmt_vid_cap(struct file *file, void *priv,
 934        struct v4l2_format *f)
 935{
 936        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
 937        struct cx23885_fmt *fmt;
 938        enum v4l2_field   field;
 939        unsigned int      maxw, maxh;
 940
 941        fmt = format_by_fourcc(f->fmt.pix.pixelformat);
 942        if (NULL == fmt)
 943                return -EINVAL;
 944
 945        field = f->fmt.pix.field;
 946        maxw  = norm_maxw(dev->tvnorm);
 947        maxh  = norm_maxh(dev->tvnorm);
 948
 949        if (V4L2_FIELD_ANY == field) {
 950                field = (f->fmt.pix.height > maxh/2)
 951                        ? V4L2_FIELD_INTERLACED
 952                        : V4L2_FIELD_BOTTOM;
 953        }
 954
 955        switch (field) {
 956        case V4L2_FIELD_TOP:
 957        case V4L2_FIELD_BOTTOM:
 958                maxh = maxh / 2;
 959                break;
 960        case V4L2_FIELD_INTERLACED:
 961                break;
 962        default:
 963                return -EINVAL;
 964        }
 965
 966        f->fmt.pix.field = field;
 967        v4l_bound_align_image(&f->fmt.pix.width, 48, maxw, 2,
 968                              &f->fmt.pix.height, 32, maxh, 0, 0);
 969        f->fmt.pix.bytesperline =
 970                (f->fmt.pix.width * fmt->depth) >> 3;
 971        f->fmt.pix.sizeimage =
 972                f->fmt.pix.height * f->fmt.pix.bytesperline;
 973
 974        return 0;
 975}
 976
 977static int vidioc_s_fmt_vid_cap(struct file *file, void *priv,
 978        struct v4l2_format *f)
 979{
 980        struct cx23885_fh *fh = priv;
 981        struct cx23885_dev *dev  = ((struct cx23885_fh *)priv)->dev;
 982        int err;
 983
 984        dprintk(2, "%s()\n", __func__);
 985        err = vidioc_try_fmt_vid_cap(file, priv, f);
 986
 987        if (0 != err)
 988                return err;
 989        fh->fmt        = format_by_fourcc(f->fmt.pix.pixelformat);
 990        fh->width      = f->fmt.pix.width;
 991        fh->height     = f->fmt.pix.height;
 992        fh->vidq.field = f->fmt.pix.field;
 993        dprintk(2, "%s() width=%d height=%d field=%d\n", __func__,
 994                fh->width, fh->height, fh->vidq.field);
 995        call_all(dev, video, s_fmt, f);
 996        return 0;
 997}
 998
 999static int vidioc_querycap(struct file *file, void  *priv,
1000        struct v4l2_capability *cap)
1001{
1002        struct cx23885_dev *dev  = ((struct cx23885_fh *)priv)->dev;
1003
1004        strcpy(cap->driver, "cx23885");
1005        strlcpy(cap->card, cx23885_boards[dev->board].name,
1006                sizeof(cap->card));
1007        sprintf(cap->bus_info, "PCIe:%s", pci_name(dev->pci));
1008        cap->version = CX23885_VERSION_CODE;
1009        cap->capabilities =
1010                V4L2_CAP_VIDEO_CAPTURE |
1011                V4L2_CAP_READWRITE     |
1012                V4L2_CAP_STREAMING     |
1013                V4L2_CAP_VBI_CAPTURE;
1014        if (UNSET != dev->tuner_type)
1015                cap->capabilities |= V4L2_CAP_TUNER;
1016        return 0;
1017}
1018
1019static int vidioc_enum_fmt_vid_cap(struct file *file, void  *priv,
1020        struct v4l2_fmtdesc *f)
1021{
1022        if (unlikely(f->index >= ARRAY_SIZE(formats)))
1023                return -EINVAL;
1024
1025        strlcpy(f->description, formats[f->index].name,
1026                sizeof(f->description));
1027        f->pixelformat = formats[f->index].fourcc;
1028
1029        return 0;
1030}
1031
1032#ifdef CONFIG_VIDEO_V4L1_COMPAT
1033static int vidiocgmbuf(struct file *file, void *priv,
1034        struct video_mbuf *mbuf)
1035{
1036        struct cx23885_fh *fh = priv;
1037        struct videobuf_queue *q;
1038        struct v4l2_requestbuffers req;
1039        unsigned int i;
1040        int err;
1041
1042        q = get_queue(fh);
1043        memset(&req, 0, sizeof(req));
1044        req.type   = q->type;
1045        req.count  = 8;
1046        req.memory = V4L2_MEMORY_MMAP;
1047        err = videobuf_reqbufs(q, &req);
1048        if (err < 0)
1049                return err;
1050
1051        mbuf->frames = req.count;
1052        mbuf->size   = 0;
1053        for (i = 0; i < mbuf->frames; i++) {
1054                mbuf->offsets[i]  = q->bufs[i]->boff;
1055                mbuf->size       += q->bufs[i]->bsize;
1056        }
1057        return 0;
1058}
1059#endif
1060
1061static int vidioc_reqbufs(struct file *file, void *priv,
1062        struct v4l2_requestbuffers *p)
1063{
1064        struct cx23885_fh *fh = priv;
1065        return videobuf_reqbufs(get_queue(fh), p);
1066}
1067
1068static int vidioc_querybuf(struct file *file, void *priv,
1069        struct v4l2_buffer *p)
1070{
1071        struct cx23885_fh *fh = priv;
1072        return videobuf_querybuf(get_queue(fh), p);
1073}
1074
1075static int vidioc_qbuf(struct file *file, void *priv,
1076        struct v4l2_buffer *p)
1077{
1078        struct cx23885_fh *fh = priv;
1079        return videobuf_qbuf(get_queue(fh), p);
1080}
1081
1082static int vidioc_dqbuf(struct file *file, void *priv,
1083        struct v4l2_buffer *p)
1084{
1085        struct cx23885_fh *fh = priv;
1086        return videobuf_dqbuf(get_queue(fh), p,
1087                                file->f_flags & O_NONBLOCK);
1088}
1089
1090static int vidioc_streamon(struct file *file, void *priv,
1091        enum v4l2_buf_type i)
1092{
1093        struct cx23885_fh *fh = priv;
1094        struct cx23885_dev *dev = fh->dev;
1095        dprintk(1, "%s()\n", __func__);
1096
1097        if (unlikely(fh->type != V4L2_BUF_TYPE_VIDEO_CAPTURE))
1098                return -EINVAL;
1099        if (unlikely(i != fh->type))
1100                return -EINVAL;
1101
1102        if (unlikely(!res_get(dev, fh, get_resource(fh))))
1103                return -EBUSY;
1104        return videobuf_streamon(get_queue(fh));
1105}
1106
1107static int vidioc_streamoff(struct file *file, void *priv, enum v4l2_buf_type i)
1108{
1109        struct cx23885_fh *fh = priv;
1110        struct cx23885_dev *dev = fh->dev;
1111        int err, res;
1112        dprintk(1, "%s()\n", __func__);
1113
1114        if (fh->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1115                return -EINVAL;
1116        if (i != fh->type)
1117                return -EINVAL;
1118
1119        res = get_resource(fh);
1120        err = videobuf_streamoff(get_queue(fh));
1121        if (err < 0)
1122                return err;
1123        res_free(dev, fh, res);
1124        return 0;
1125}
1126
1127static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *tvnorms)
1128{
1129        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1130        dprintk(1, "%s()\n", __func__);
1131
1132        mutex_lock(&dev->lock);
1133        cx23885_set_tvnorm(dev, *tvnorms);
1134        mutex_unlock(&dev->lock);
1135
1136        return 0;
1137}
1138
1139static int cx23885_enum_input(struct cx23885_dev *dev, struct v4l2_input *i)
1140{
1141        static const char *iname[] = {
1142                [CX23885_VMUX_COMPOSITE1] = "Composite1",
1143                [CX23885_VMUX_COMPOSITE2] = "Composite2",
1144                [CX23885_VMUX_COMPOSITE3] = "Composite3",
1145                [CX23885_VMUX_COMPOSITE4] = "Composite4",
1146                [CX23885_VMUX_SVIDEO]     = "S-Video",
1147                [CX23885_VMUX_TELEVISION] = "Television",
1148                [CX23885_VMUX_CABLE]      = "Cable TV",
1149                [CX23885_VMUX_DVB]        = "DVB",
1150                [CX23885_VMUX_DEBUG]      = "for debug only",
1151        };
1152        unsigned int n;
1153        dprintk(1, "%s()\n", __func__);
1154
1155        n = i->index;
1156        if (n >= 4)
1157                return -EINVAL;
1158
1159        if (0 == INPUT(n)->type)
1160                return -EINVAL;
1161
1162        memset(i, 0, sizeof(*i));
1163        i->index = n;
1164        i->type  = V4L2_INPUT_TYPE_CAMERA;
1165        strcpy(i->name, iname[INPUT(n)->type]);
1166        if ((CX23885_VMUX_TELEVISION == INPUT(n)->type) ||
1167                (CX23885_VMUX_CABLE == INPUT(n)->type))
1168                i->type = V4L2_INPUT_TYPE_TUNER;
1169                i->std = CX23885_NORMS;
1170        return 0;
1171}
1172
1173static int vidioc_enum_input(struct file *file, void *priv,
1174                                struct v4l2_input *i)
1175{
1176        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1177        dprintk(1, "%s()\n", __func__);
1178        return cx23885_enum_input(dev, i);
1179}
1180
1181static int vidioc_g_input(struct file *file, void *priv, unsigned int *i)
1182{
1183        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1184
1185        *i = dev->input;
1186        dprintk(1, "%s() returns %d\n", __func__, *i);
1187        return 0;
1188}
1189
1190static int vidioc_s_input(struct file *file, void *priv, unsigned int i)
1191{
1192        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1193
1194        dprintk(1, "%s(%d)\n", __func__, i);
1195
1196        if (i >= 4) {
1197                dprintk(1, "%s() -EINVAL\n", __func__);
1198                return -EINVAL;
1199        }
1200
1201        mutex_lock(&dev->lock);
1202        cx23885_video_mux(dev, i);
1203        mutex_unlock(&dev->lock);
1204        return 0;
1205}
1206
1207static int vidioc_queryctrl(struct file *file, void *priv,
1208                                struct v4l2_queryctrl *qctrl)
1209{
1210        qctrl->id = v4l2_ctrl_next(ctrl_classes, qctrl->id);
1211        if (unlikely(qctrl->id == 0))
1212                return -EINVAL;
1213        return cx23885_ctrl_query(qctrl);
1214}
1215
1216static int vidioc_g_ctrl(struct file *file, void *priv,
1217                                struct v4l2_control *ctl)
1218{
1219        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1220
1221        return cx23885_get_control(dev, ctl);
1222}
1223
1224static int vidioc_s_ctrl(struct file *file, void *priv,
1225                                struct v4l2_control *ctl)
1226{
1227        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1228
1229        return cx23885_set_control(dev, ctl);
1230}
1231
1232static int vidioc_g_tuner(struct file *file, void *priv,
1233                                struct v4l2_tuner *t)
1234{
1235        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1236
1237        if (unlikely(UNSET == dev->tuner_type))
1238                return -EINVAL;
1239        if (0 != t->index)
1240                return -EINVAL;
1241
1242        strcpy(t->name, "Television");
1243        t->type       = V4L2_TUNER_ANALOG_TV;
1244        t->capability = V4L2_TUNER_CAP_NORM;
1245        t->rangehigh  = 0xffffffffUL;
1246        t->signal = 0xffff ; /* LOCKED */
1247        return 0;
1248}
1249
1250static int vidioc_s_tuner(struct file *file, void *priv,
1251                                struct v4l2_tuner *t)
1252{
1253        struct cx23885_dev *dev = ((struct cx23885_fh *)priv)->dev;
1254
1255        if (UNSET == dev->tuner_type)
1256                return -EINVAL;
1257        if (0 != t->index)
1258                return -EINVAL;
1259        return 0;
1260}
1261
1262static int vidioc_g_frequency(struct file *file, void *priv,
1263                                struct v4l2_frequency *f)
1264{
1265        struct cx23885_fh *fh = priv;
1266        struct cx23885_dev *dev = fh->dev;
1267
1268        if (unlikely(UNSET == dev->tuner_type))
1269                return -EINVAL;
1270
1271        /* f->type = fh->radio ? V4L2_TUNER_RADIO : V4L2_TUNER_ANALOG_TV; */
1272        f->type = fh->radio ? V4L2_TUNER_RADIO : V4L2_TUNER_ANALOG_TV;
1273        f->frequency = dev->freq;
1274
1275        call_all(dev, tuner, g_frequency, f);
1276
1277        return 0;
1278}
1279
1280static int cx23885_set_freq(struct cx23885_dev *dev, struct v4l2_frequency *f)
1281{
1282        if (unlikely(UNSET == dev->tuner_type))
1283                return -EINVAL;
1284        if (unlikely(f->tuner != 0))
1285                return -EINVAL;
1286
1287        mutex_lock(&dev->lock);
1288        dev->freq = f->frequency;
1289
1290        call_all(dev, tuner, s_frequency, f);
1291
1292        /* When changing channels it is required to reset TVAUDIO */
1293        msleep(10);
1294
1295        mutex_unlock(&dev->lock);
1296
1297        return 0;
1298}
1299
1300static int vidioc_s_frequency(struct file *file, void *priv,
1301                                struct v4l2_frequency *f)
1302{
1303        struct cx23885_fh *fh = priv;
1304        struct cx23885_dev *dev = fh->dev;
1305
1306        if (unlikely(0 == fh->radio && f->type != V4L2_TUNER_ANALOG_TV))
1307                return -EINVAL;
1308        if (unlikely(1 == fh->radio && f->type != V4L2_TUNER_RADIO))
1309                return -EINVAL;
1310
1311        return
1312                cx23885_set_freq(dev, f);
1313}
1314
1315#ifdef CONFIG_VIDEO_ADV_DEBUG
1316static int vidioc_g_register(struct file *file, void *fh,
1317                                struct v4l2_dbg_register *reg)
1318{
1319        struct cx23885_dev *dev = ((struct cx23885_fh *)fh)->dev;
1320
1321        if (!v4l2_chip_match_host(&reg->match))
1322                return -EINVAL;
1323
1324        call_all(dev, core, g_register, reg);
1325
1326        return 0;
1327}
1328
1329static int vidioc_s_register(struct file *file, void *fh,
1330                                struct v4l2_dbg_register *reg)
1331{
1332        struct cx23885_dev *dev = ((struct cx23885_fh *)fh)->dev;
1333
1334        if (!v4l2_chip_match_host(&reg->match))
1335                return -EINVAL;
1336
1337        call_all(dev, core, s_register, reg);
1338
1339        return 0;
1340}
1341#endif
1342
1343/* ----------------------------------------------------------- */
1344
1345static void cx23885_vid_timeout(unsigned long data)
1346{
1347        struct cx23885_dev *dev = (struct cx23885_dev *)data;
1348        struct cx23885_dmaqueue *q = &dev->vidq;
1349        struct cx23885_buffer *buf;
1350        unsigned long flags;
1351
1352        cx23885_sram_channel_dump(dev, &dev->sram_channels[SRAM_CH01]);
1353
1354        cx_clear(VID_A_DMA_CTL, 0x11);
1355
1356        spin_lock_irqsave(&dev->slock, flags);
1357        while (!list_empty(&q->active)) {
1358                buf = list_entry(q->active.next,
1359                        struct cx23885_buffer, vb.queue);
1360                list_del(&buf->vb.queue);
1361                buf->vb.state = VIDEOBUF_ERROR;
1362                wake_up(&buf->vb.done);
1363                printk(KERN_ERR "%s/0: [%p/%d] timeout - dma=0x%08lx\n",
1364                        dev->name, buf, buf->vb.i,
1365                        (unsigned long)buf->risc.dma);
1366        }
1367        cx23885_restart_video_queue(dev, q);
1368        spin_unlock_irqrestore(&dev->slock, flags);
1369}
1370
1371int cx23885_video_irq(struct cx23885_dev *dev, u32 status)
1372{
1373        u32 mask, count;
1374        int handled = 0;
1375
1376        mask   = cx_read(VID_A_INT_MSK);
1377        if (0 == (status & mask))
1378                return handled;
1379        cx_write(VID_A_INT_STAT, status);
1380
1381        dprintk(2, "%s() status = 0x%08x\n", __func__, status);
1382        /* risc op code error */
1383        if (status & (1 << 16)) {
1384                printk(KERN_WARNING "%s/0: video risc op code error\n",
1385                        dev->name);
1386                cx_clear(VID_A_DMA_CTL, 0x11);
1387                cx23885_sram_channel_dump(dev, &dev->sram_channels[SRAM_CH01]);
1388        }
1389
1390        /* risc1 y */
1391        if (status & 0x01) {
1392                spin_lock(&dev->slock);
1393                count = cx_read(VID_A_GPCNT);
1394                cx23885_video_wakeup(dev, &dev->vidq, count);
1395                spin_unlock(&dev->slock);
1396                handled++;
1397        }
1398        /* risc2 y */
1399        if (status & 0x10) {
1400                dprintk(2, "stopper video\n");
1401                spin_lock(&dev->slock);
1402                cx23885_restart_video_queue(dev, &dev->vidq);
1403                spin_unlock(&dev->slock);
1404                handled++;
1405        }
1406
1407        return handled;
1408}
1409
1410/* ----------------------------------------------------------- */
1411/* exported stuff                                              */
1412
1413static const struct v4l2_file_operations video_fops = {
1414        .owner         = THIS_MODULE,
1415        .open          = video_open,
1416        .release       = video_release,
1417        .read          = video_read,
1418        .poll          = video_poll,
1419        .mmap          = video_mmap,
1420        .ioctl         = video_ioctl2,
1421};
1422
1423static const struct v4l2_ioctl_ops video_ioctl_ops = {
1424        .vidioc_querycap      = vidioc_querycap,
1425        .vidioc_enum_fmt_vid_cap  = vidioc_enum_fmt_vid_cap,
1426        .vidioc_g_fmt_vid_cap     = vidioc_g_fmt_vid_cap,
1427        .vidioc_try_fmt_vid_cap   = vidioc_try_fmt_vid_cap,
1428        .vidioc_s_fmt_vid_cap     = vidioc_s_fmt_vid_cap,
1429        .vidioc_g_fmt_vbi_cap     = cx23885_vbi_fmt,
1430        .vidioc_try_fmt_vbi_cap   = cx23885_vbi_fmt,
1431        .vidioc_s_fmt_vbi_cap     = cx23885_vbi_fmt,
1432        .vidioc_reqbufs       = vidioc_reqbufs,
1433        .vidioc_querybuf      = vidioc_querybuf,
1434        .vidioc_qbuf          = vidioc_qbuf,
1435        .vidioc_dqbuf         = vidioc_dqbuf,
1436        .vidioc_s_std         = vidioc_s_std,
1437        .vidioc_enum_input    = vidioc_enum_input,
1438        .vidioc_g_input       = vidioc_g_input,
1439        .vidioc_s_input       = vidioc_s_input,
1440        .vidioc_queryctrl     = vidioc_queryctrl,
1441        .vidioc_g_ctrl        = vidioc_g_ctrl,
1442        .vidioc_s_ctrl        = vidioc_s_ctrl,
1443        .vidioc_streamon      = vidioc_streamon,
1444        .vidioc_streamoff     = vidioc_streamoff,
1445#ifdef CONFIG_VIDEO_V4L1_COMPAT
1446        .vidiocgmbuf          = vidiocgmbuf,
1447#endif
1448        .vidioc_g_tuner       = vidioc_g_tuner,
1449        .vidioc_s_tuner       = vidioc_s_tuner,
1450        .vidioc_g_frequency   = vidioc_g_frequency,
1451        .vidioc_s_frequency   = vidioc_s_frequency,
1452#ifdef CONFIG_VIDEO_ADV_DEBUG
1453        .vidioc_g_register    = vidioc_g_register,
1454        .vidioc_s_register    = vidioc_s_register,
1455#endif
1456};
1457
1458static struct video_device cx23885_vbi_template;
1459static struct video_device cx23885_video_template = {
1460        .name                 = "cx23885-video",
1461        .fops                 = &video_fops,
1462        .minor                = -1,
1463        .ioctl_ops            = &video_ioctl_ops,
1464        .tvnorms              = CX23885_NORMS,
1465        .current_norm         = V4L2_STD_NTSC_M,
1466};
1467
1468static const struct v4l2_file_operations radio_fops = {
1469        .owner         = THIS_MODULE,
1470        .open          = video_open,
1471        .release       = video_release,
1472        .ioctl         = video_ioctl2,
1473};
1474
1475
1476void cx23885_video_unregister(struct cx23885_dev *dev)
1477{
1478        dprintk(1, "%s()\n", __func__);
1479        cx_clear(PCI_INT_MSK, 1);
1480
1481        if (dev->video_dev) {
1482                if (-1 != dev->video_dev->minor)
1483                        video_unregister_device(dev->video_dev);
1484                else
1485                        video_device_release(dev->video_dev);
1486                dev->video_dev = NULL;
1487
1488                btcx_riscmem_free(dev->pci, &dev->vidq.stopper);
1489        }
1490}
1491
1492int cx23885_video_register(struct cx23885_dev *dev)
1493{
1494        int err;
1495
1496        dprintk(1, "%s()\n", __func__);
1497        spin_lock_init(&dev->slock);
1498
1499        /* Initialize VBI template */
1500        memcpy(&cx23885_vbi_template, &cx23885_video_template,
1501                sizeof(cx23885_vbi_template));
1502        strcpy(cx23885_vbi_template.name, "cx23885-vbi");
1503
1504        dev->tvnorm = cx23885_video_template.current_norm;
1505
1506        /* init video dma queues */
1507        INIT_LIST_HEAD(&dev->vidq.active);
1508        INIT_LIST_HEAD(&dev->vidq.queued);
1509        dev->vidq.timeout.function = cx23885_vid_timeout;
1510        dev->vidq.timeout.data = (unsigned long)dev;
1511        init_timer(&dev->vidq.timeout);
1512        cx23885_risc_stopper(dev->pci, &dev->vidq.stopper,
1513                VID_A_DMA_CTL, 0x11, 0x00);
1514
1515        /* Don't enable VBI yet */
1516        cx_set(PCI_INT_MSK, 1);
1517
1518        if (TUNER_ABSENT != dev->tuner_type) {
1519                struct v4l2_subdev *sd = NULL;
1520
1521                if (dev->tuner_addr)
1522                        sd = v4l2_i2c_new_subdev(&dev->v4l2_dev,
1523                                &dev->i2c_bus[1].i2c_adap,
1524                                "tuner", "tuner", dev->tuner_addr, NULL);
1525                else
1526                        sd = v4l2_i2c_new_subdev(&dev->v4l2_dev,
1527                                &dev->i2c_bus[1].i2c_adap,
1528                                "tuner", "tuner", 0, v4l2_i2c_tuner_addrs(ADDRS_TV));
1529                if (sd) {
1530                        struct tuner_setup tun_setup;
1531
1532                        tun_setup.mode_mask = T_ANALOG_TV;
1533                        tun_setup.type = dev->tuner_type;
1534                        tun_setup.addr = v4l2_i2c_subdev_addr(sd);
1535
1536                        v4l2_subdev_call(sd, tuner, s_type_addr, &tun_setup);
1537                }
1538        }
1539
1540
1541        /* register v4l devices */
1542        dev->video_dev = cx23885_vdev_init(dev, dev->pci,
1543                &cx23885_video_template, "video");
1544        err = video_register_device(dev->video_dev, VFL_TYPE_GRABBER,
1545                                    video_nr[dev->nr]);
1546        if (err < 0) {
1547                printk(KERN_INFO "%s: can't register video device\n",
1548                        dev->name);
1549                goto fail_unreg;
1550        }
1551        printk(KERN_INFO "%s/0: registered device video%d [v4l2]\n",
1552               dev->name, dev->video_dev->num);
1553        /* initial device configuration */
1554        mutex_lock(&dev->lock);
1555        cx23885_set_tvnorm(dev, dev->tvnorm);
1556        init_controls(dev);
1557        cx23885_video_mux(dev, 0);
1558        mutex_unlock(&dev->lock);
1559
1560        return 0;
1561
1562fail_unreg:
1563        cx23885_video_unregister(dev);
1564        return err;
1565}
1566
1567