linux/drivers/media/platform/davinci/vpbe_display.c
<<
>>
Prefs
   1/*
   2 * Copyright (C) 2010 Texas Instruments Incorporated - http://www.ti.com/
   3 *
   4 * This program is free software; you can redistribute it and/or
   5 * modify it under the terms of the GNU General Public License as
   6 * published by the Free Software Foundation version 2.
   7 *
   8 * This program is distributed WITHOUT ANY WARRANTY of any
   9 * kind, whether express or implied; without even the implied warranty
  10 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  11 * GNU General Public License for more details.
  12 */
  13#include <linux/kernel.h>
  14#include <linux/init.h>
  15#include <linux/module.h>
  16#include <linux/errno.h>
  17#include <linux/interrupt.h>
  18#include <linux/string.h>
  19#include <linux/wait.h>
  20#include <linux/time.h>
  21#include <linux/platform_device.h>
  22#include <linux/irq.h>
  23#include <linux/mm.h>
  24#include <linux/mutex.h>
  25#include <linux/videodev2.h>
  26#include <linux/slab.h>
  27
  28#include <asm/pgtable.h>
  29#include <mach/cputype.h>
  30
  31#include <media/v4l2-dev.h>
  32#include <media/v4l2-common.h>
  33#include <media/v4l2-ioctl.h>
  34#include <media/v4l2-device.h>
  35#include <media/davinci/vpbe_display.h>
  36#include <media/davinci/vpbe_types.h>
  37#include <media/davinci/vpbe.h>
  38#include <media/davinci/vpbe_venc.h>
  39#include <media/davinci/vpbe_osd.h>
  40#include "vpbe_venc_regs.h"
  41
  42#define VPBE_DISPLAY_DRIVER "vpbe-v4l2"
  43
  44static int debug;
  45
  46#define VPBE_DEFAULT_NUM_BUFS 3
  47
  48module_param(debug, int, 0644);
  49
  50static int vpbe_set_osd_display_params(struct vpbe_display *disp_dev,
  51                        struct vpbe_layer *layer);
  52
  53static int venc_is_second_field(struct vpbe_display *disp_dev)
  54{
  55        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
  56        int ret;
  57        int val;
  58
  59        ret = v4l2_subdev_call(vpbe_dev->venc,
  60                               core,
  61                               ioctl,
  62                               VENC_GET_FLD,
  63                               &val);
  64        if (ret < 0) {
  65                v4l2_err(&vpbe_dev->v4l2_dev,
  66                         "Error in getting Field ID 0\n");
  67        }
  68        return val;
  69}
  70
  71static void vpbe_isr_even_field(struct vpbe_display *disp_obj,
  72                                struct vpbe_layer *layer)
  73{
  74        struct timespec timevalue;
  75
  76        if (layer->cur_frm == layer->next_frm)
  77                return;
  78        ktime_get_ts(&timevalue);
  79        layer->cur_frm->vb.v4l2_buf.timestamp.tv_sec =
  80                timevalue.tv_sec;
  81        layer->cur_frm->vb.v4l2_buf.timestamp.tv_usec =
  82                timevalue.tv_nsec / NSEC_PER_USEC;
  83        vb2_buffer_done(&layer->cur_frm->vb, VB2_BUF_STATE_DONE);
  84        /* Make cur_frm pointing to next_frm */
  85        layer->cur_frm = layer->next_frm;
  86}
  87
  88static void vpbe_isr_odd_field(struct vpbe_display *disp_obj,
  89                                struct vpbe_layer *layer)
  90{
  91        struct osd_state *osd_device = disp_obj->osd_device;
  92        unsigned long addr;
  93
  94        spin_lock(&disp_obj->dma_queue_lock);
  95        if (list_empty(&layer->dma_queue) ||
  96                (layer->cur_frm != layer->next_frm)) {
  97                spin_unlock(&disp_obj->dma_queue_lock);
  98                return;
  99        }
 100        /*
 101         * one field is displayed configure
 102         * the next frame if it is available
 103         * otherwise hold on current frame
 104         * Get next from the buffer queue
 105         */
 106        layer->next_frm = list_entry(layer->dma_queue.next,
 107                          struct  vpbe_disp_buffer, list);
 108        /* Remove that from the buffer queue */
 109        list_del(&layer->next_frm->list);
 110        spin_unlock(&disp_obj->dma_queue_lock);
 111        /* Mark state of the frame to active */
 112        layer->next_frm->vb.state = VB2_BUF_STATE_ACTIVE;
 113        addr = vb2_dma_contig_plane_dma_addr(&layer->next_frm->vb, 0);
 114        osd_device->ops.start_layer(osd_device,
 115                        layer->layer_info.id,
 116                        addr,
 117                        disp_obj->cbcr_ofst);
 118}
 119
 120/* interrupt service routine */
 121static irqreturn_t venc_isr(int irq, void *arg)
 122{
 123        struct vpbe_display *disp_dev = (struct vpbe_display *)arg;
 124        struct vpbe_layer *layer;
 125        static unsigned last_event;
 126        unsigned event = 0;
 127        int fid;
 128        int i;
 129
 130        if ((NULL == arg) || (NULL == disp_dev->dev[0]))
 131                return IRQ_HANDLED;
 132
 133        if (venc_is_second_field(disp_dev))
 134                event |= VENC_SECOND_FIELD;
 135        else
 136                event |= VENC_FIRST_FIELD;
 137
 138        if (event == (last_event & ~VENC_END_OF_FRAME)) {
 139                /*
 140                * If the display is non-interlaced, then we need to flag the
 141                * end-of-frame event at every interrupt regardless of the
 142                * value of the FIDST bit.  We can conclude that the display is
 143                * non-interlaced if the value of the FIDST bit is unchanged
 144                * from the previous interrupt.
 145                */
 146                event |= VENC_END_OF_FRAME;
 147        } else if (event == VENC_SECOND_FIELD) {
 148                /* end-of-frame for interlaced display */
 149                event |= VENC_END_OF_FRAME;
 150        }
 151        last_event = event;
 152
 153        for (i = 0; i < VPBE_DISPLAY_MAX_DEVICES; i++) {
 154                layer = disp_dev->dev[i];
 155                /* If streaming is started in this layer */
 156                if (!layer->started)
 157                        continue;
 158
 159                if (layer->layer_first_int) {
 160                        layer->layer_first_int = 0;
 161                        continue;
 162                }
 163                /* Check the field format */
 164                if ((V4L2_FIELD_NONE == layer->pix_fmt.field) &&
 165                        (event & VENC_END_OF_FRAME)) {
 166                        /* Progressive mode */
 167
 168                        vpbe_isr_even_field(disp_dev, layer);
 169                        vpbe_isr_odd_field(disp_dev, layer);
 170                } else {
 171                /* Interlaced mode */
 172
 173                        layer->field_id ^= 1;
 174                        if (event & VENC_FIRST_FIELD)
 175                                fid = 0;
 176                        else
 177                                fid = 1;
 178
 179                        /*
 180                        * If field id does not match with store
 181                        * field id
 182                        */
 183                        if (fid != layer->field_id) {
 184                                /* Make them in sync */
 185                                layer->field_id = fid;
 186                                continue;
 187                        }
 188                        /*
 189                        * device field id and local field id are
 190                        * in sync. If this is even field
 191                        */
 192                        if (0 == fid)
 193                                vpbe_isr_even_field(disp_dev, layer);
 194                        else  /* odd field */
 195                                vpbe_isr_odd_field(disp_dev, layer);
 196                }
 197        }
 198
 199        return IRQ_HANDLED;
 200}
 201
 202/*
 203 * vpbe_buffer_prepare()
 204 * This is the callback function called from vb2_qbuf() function
 205 * the buffer is prepared and user space virtual address is converted into
 206 * physical address
 207 */
 208static int vpbe_buffer_prepare(struct vb2_buffer *vb)
 209{
 210        struct vpbe_fh *fh = vb2_get_drv_priv(vb->vb2_queue);
 211        struct vb2_queue *q = vb->vb2_queue;
 212        struct vpbe_layer *layer = fh->layer;
 213        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 214        unsigned long addr;
 215
 216        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 217                                "vpbe_buffer_prepare\n");
 218
 219        if (vb->state != VB2_BUF_STATE_ACTIVE &&
 220                vb->state != VB2_BUF_STATE_PREPARED) {
 221                vb2_set_plane_payload(vb, 0, layer->pix_fmt.sizeimage);
 222                if (vb2_plane_vaddr(vb, 0) &&
 223                vb2_get_plane_payload(vb, 0) > vb2_plane_size(vb, 0))
 224                        return -EINVAL;
 225
 226                addr = vb2_dma_contig_plane_dma_addr(vb, 0);
 227                if (q->streaming) {
 228                        if (!IS_ALIGNED(addr, 8)) {
 229                                v4l2_err(&vpbe_dev->v4l2_dev,
 230                                        "buffer_prepare:offset is \
 231                                        not aligned to 32 bytes\n");
 232                                return -EINVAL;
 233                        }
 234                }
 235        }
 236        return 0;
 237}
 238
 239/*
 240 * vpbe_buffer_setup()
 241 * This function allocates memory for the buffers
 242 */
 243static int
 244vpbe_buffer_queue_setup(struct vb2_queue *vq, const struct v4l2_format *fmt,
 245                        unsigned int *nbuffers, unsigned int *nplanes,
 246                        unsigned int sizes[], void *alloc_ctxs[])
 247
 248{
 249        /* Get the file handle object and layer object */
 250        struct vpbe_fh *fh = vb2_get_drv_priv(vq);
 251        struct vpbe_layer *layer = fh->layer;
 252        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 253
 254        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_buffer_setup\n");
 255
 256        /* Store number of buffers allocated in numbuffer member */
 257        if (*nbuffers < VPBE_DEFAULT_NUM_BUFS)
 258                *nbuffers = layer->numbuffers = VPBE_DEFAULT_NUM_BUFS;
 259
 260        *nplanes = 1;
 261        sizes[0] = layer->pix_fmt.sizeimage;
 262        alloc_ctxs[0] = layer->alloc_ctx;
 263
 264        return 0;
 265}
 266
 267/*
 268 * vpbe_buffer_queue()
 269 * This function adds the buffer to DMA queue
 270 */
 271static void vpbe_buffer_queue(struct vb2_buffer *vb)
 272{
 273        /* Get the file handle object and layer object */
 274        struct vpbe_fh *fh = vb2_get_drv_priv(vb->vb2_queue);
 275        struct vpbe_disp_buffer *buf = container_of(vb,
 276                                struct vpbe_disp_buffer, vb);
 277        struct vpbe_layer *layer = fh->layer;
 278        struct vpbe_display *disp = fh->disp_dev;
 279        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 280        unsigned long flags;
 281
 282        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 283                        "vpbe_buffer_queue\n");
 284
 285        /* add the buffer to the DMA queue */
 286        spin_lock_irqsave(&disp->dma_queue_lock, flags);
 287        list_add_tail(&buf->list, &layer->dma_queue);
 288        spin_unlock_irqrestore(&disp->dma_queue_lock, flags);
 289}
 290
 291/*
 292 * vpbe_buf_cleanup()
 293 * This function is called from the vb2 layer to free memory allocated to
 294 * the buffers
 295 */
 296static void vpbe_buf_cleanup(struct vb2_buffer *vb)
 297{
 298        /* Get the file handle object and layer object */
 299        struct vpbe_fh *fh = vb2_get_drv_priv(vb->vb2_queue);
 300        struct vpbe_layer *layer = fh->layer;
 301        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 302        struct vpbe_disp_buffer *buf = container_of(vb,
 303                                        struct vpbe_disp_buffer, vb);
 304        unsigned long flags;
 305
 306        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 307                        "vpbe_buf_cleanup\n");
 308
 309        spin_lock_irqsave(&layer->irqlock, flags);
 310        if (vb->state == VB2_BUF_STATE_ACTIVE)
 311                list_del_init(&buf->list);
 312        spin_unlock_irqrestore(&layer->irqlock, flags);
 313}
 314
 315static void vpbe_wait_prepare(struct vb2_queue *vq)
 316{
 317        struct vpbe_fh *fh = vb2_get_drv_priv(vq);
 318        struct vpbe_layer *layer = fh->layer;
 319
 320        mutex_unlock(&layer->opslock);
 321}
 322
 323static void vpbe_wait_finish(struct vb2_queue *vq)
 324{
 325        struct vpbe_fh *fh = vb2_get_drv_priv(vq);
 326        struct vpbe_layer *layer = fh->layer;
 327
 328        mutex_lock(&layer->opslock);
 329}
 330
 331static int vpbe_buffer_init(struct vb2_buffer *vb)
 332{
 333        struct vpbe_disp_buffer *buf = container_of(vb,
 334                                        struct vpbe_disp_buffer, vb);
 335
 336        INIT_LIST_HEAD(&buf->list);
 337        return 0;
 338}
 339
 340static int vpbe_start_streaming(struct vb2_queue *vq, unsigned int count)
 341{
 342        struct vpbe_fh *fh = vb2_get_drv_priv(vq);
 343        struct vpbe_layer *layer = fh->layer;
 344        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 345        int ret;
 346
 347        /* If buffer queue is empty, return error */
 348        if (list_empty(&layer->dma_queue)) {
 349                v4l2_err(&vpbe_dev->v4l2_dev, "buffer queue is empty\n");
 350                return -EINVAL;
 351        }
 352        /* Get the next frame from the buffer queue */
 353        layer->next_frm = layer->cur_frm = list_entry(layer->dma_queue.next,
 354                                struct vpbe_disp_buffer, list);
 355        /* Remove buffer from the buffer queue */
 356        list_del(&layer->cur_frm->list);
 357        /* Mark state of the current frame to active */
 358        layer->cur_frm->vb.state = VB2_BUF_STATE_ACTIVE;
 359        /* Initialize field_id and started member */
 360        layer->field_id = 0;
 361
 362        /* Set parameters in OSD and VENC */
 363        ret = vpbe_set_osd_display_params(fh->disp_dev, layer);
 364        if (ret < 0)
 365                return ret;
 366
 367        /*
 368         * if request format is yuv420 semiplanar, need to
 369         * enable both video windows
 370         */
 371        layer->started = 1;
 372        layer->layer_first_int = 1;
 373
 374        return ret;
 375}
 376
 377static int vpbe_stop_streaming(struct vb2_queue *vq)
 378{
 379        struct vpbe_fh *fh = vb2_get_drv_priv(vq);
 380        struct vpbe_layer *layer = fh->layer;
 381
 382        if (!vb2_is_streaming(vq))
 383                return 0;
 384
 385        /* release all active buffers */
 386        while (!list_empty(&layer->dma_queue)) {
 387                layer->next_frm = list_entry(layer->dma_queue.next,
 388                                                struct vpbe_disp_buffer, list);
 389                list_del(&layer->next_frm->list);
 390                vb2_buffer_done(&layer->next_frm->vb, VB2_BUF_STATE_ERROR);
 391        }
 392
 393        return 0;
 394}
 395
 396static struct vb2_ops video_qops = {
 397        .queue_setup = vpbe_buffer_queue_setup,
 398        .wait_prepare = vpbe_wait_prepare,
 399        .wait_finish = vpbe_wait_finish,
 400        .buf_init = vpbe_buffer_init,
 401        .buf_prepare = vpbe_buffer_prepare,
 402        .start_streaming = vpbe_start_streaming,
 403        .stop_streaming = vpbe_stop_streaming,
 404        .buf_cleanup = vpbe_buf_cleanup,
 405        .buf_queue = vpbe_buffer_queue,
 406};
 407
 408static
 409struct vpbe_layer*
 410_vpbe_display_get_other_win_layer(struct vpbe_display *disp_dev,
 411                        struct vpbe_layer *layer)
 412{
 413        enum vpbe_display_device_id thiswin, otherwin;
 414        thiswin = layer->device_id;
 415
 416        otherwin = (thiswin == VPBE_DISPLAY_DEVICE_0) ?
 417        VPBE_DISPLAY_DEVICE_1 : VPBE_DISPLAY_DEVICE_0;
 418        return disp_dev->dev[otherwin];
 419}
 420
 421static int vpbe_set_osd_display_params(struct vpbe_display *disp_dev,
 422                        struct vpbe_layer *layer)
 423{
 424        struct osd_layer_config *cfg  = &layer->layer_info.config;
 425        struct osd_state *osd_device = disp_dev->osd_device;
 426        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 427        unsigned long addr;
 428        int ret;
 429
 430        addr = vb2_dma_contig_plane_dma_addr(&layer->cur_frm->vb, 0);
 431        /* Set address in the display registers */
 432        osd_device->ops.start_layer(osd_device,
 433                                    layer->layer_info.id,
 434                                    addr,
 435                                    disp_dev->cbcr_ofst);
 436
 437        ret = osd_device->ops.enable_layer(osd_device,
 438                                layer->layer_info.id, 0);
 439        if (ret < 0) {
 440                v4l2_err(&vpbe_dev->v4l2_dev,
 441                        "Error in enabling osd window layer 0\n");
 442                return -1;
 443        }
 444
 445        /* Enable the window */
 446        layer->layer_info.enable = 1;
 447        if (cfg->pixfmt == PIXFMT_NV12) {
 448                struct vpbe_layer *otherlayer =
 449                        _vpbe_display_get_other_win_layer(disp_dev, layer);
 450
 451                ret = osd_device->ops.enable_layer(osd_device,
 452                                otherlayer->layer_info.id, 1);
 453                if (ret < 0) {
 454                        v4l2_err(&vpbe_dev->v4l2_dev,
 455                                "Error in enabling osd window layer 1\n");
 456                        return -1;
 457                }
 458                otherlayer->layer_info.enable = 1;
 459        }
 460        return 0;
 461}
 462
 463static void
 464vpbe_disp_calculate_scale_factor(struct vpbe_display *disp_dev,
 465                        struct vpbe_layer *layer,
 466                        int expected_xsize, int expected_ysize)
 467{
 468        struct display_layer_info *layer_info = &layer->layer_info;
 469        struct v4l2_pix_format *pixfmt = &layer->pix_fmt;
 470        struct osd_layer_config *cfg  = &layer->layer_info.config;
 471        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 472        int calculated_xsize;
 473        int h_exp = 0;
 474        int v_exp = 0;
 475        int h_scale;
 476        int v_scale;
 477
 478        v4l2_std_id standard_id = vpbe_dev->current_timings.std_id;
 479
 480        /*
 481         * Application initially set the image format. Current display
 482         * size is obtained from the vpbe display controller. expected_xsize
 483         * and expected_ysize are set through S_CROP ioctl. Based on this,
 484         * driver will calculate the scale factors for vertical and
 485         * horizontal direction so that the image is displayed scaled
 486         * and expanded. Application uses expansion to display the image
 487         * in a square pixel. Otherwise it is displayed using displays
 488         * pixel aspect ratio.It is expected that application chooses
 489         * the crop coordinates for cropped or scaled display. if crop
 490         * size is less than the image size, it is displayed cropped or
 491         * it is displayed scaled and/or expanded.
 492         *
 493         * to begin with, set the crop window same as expected. Later we
 494         * will override with scaled window size
 495         */
 496
 497        cfg->xsize = pixfmt->width;
 498        cfg->ysize = pixfmt->height;
 499        layer_info->h_zoom = ZOOM_X1;   /* no horizontal zoom */
 500        layer_info->v_zoom = ZOOM_X1;   /* no horizontal zoom */
 501        layer_info->h_exp = H_EXP_OFF;  /* no horizontal zoom */
 502        layer_info->v_exp = V_EXP_OFF;  /* no horizontal zoom */
 503
 504        if (pixfmt->width < expected_xsize) {
 505                h_scale = vpbe_dev->current_timings.xres / pixfmt->width;
 506                if (h_scale < 2)
 507                        h_scale = 1;
 508                else if (h_scale >= 4)
 509                        h_scale = 4;
 510                else
 511                        h_scale = 2;
 512                cfg->xsize *= h_scale;
 513                if (cfg->xsize < expected_xsize) {
 514                        if ((standard_id & V4L2_STD_525_60) ||
 515                        (standard_id & V4L2_STD_625_50)) {
 516                                calculated_xsize = (cfg->xsize *
 517                                        VPBE_DISPLAY_H_EXP_RATIO_N) /
 518                                        VPBE_DISPLAY_H_EXP_RATIO_D;
 519                                if (calculated_xsize <= expected_xsize) {
 520                                        h_exp = 1;
 521                                        cfg->xsize = calculated_xsize;
 522                                }
 523                        }
 524                }
 525                if (h_scale == 2)
 526                        layer_info->h_zoom = ZOOM_X2;
 527                else if (h_scale == 4)
 528                        layer_info->h_zoom = ZOOM_X4;
 529                if (h_exp)
 530                        layer_info->h_exp = H_EXP_9_OVER_8;
 531        } else {
 532                /* no scaling, only cropping. Set display area to crop area */
 533                cfg->xsize = expected_xsize;
 534        }
 535
 536        if (pixfmt->height < expected_ysize) {
 537                v_scale = expected_ysize / pixfmt->height;
 538                if (v_scale < 2)
 539                        v_scale = 1;
 540                else if (v_scale >= 4)
 541                        v_scale = 4;
 542                else
 543                        v_scale = 2;
 544                cfg->ysize *= v_scale;
 545                if (cfg->ysize < expected_ysize) {
 546                        if ((standard_id & V4L2_STD_625_50)) {
 547                                calculated_xsize = (cfg->ysize *
 548                                        VPBE_DISPLAY_V_EXP_RATIO_N) /
 549                                        VPBE_DISPLAY_V_EXP_RATIO_D;
 550                                if (calculated_xsize <= expected_ysize) {
 551                                        v_exp = 1;
 552                                        cfg->ysize = calculated_xsize;
 553                                }
 554                        }
 555                }
 556                if (v_scale == 2)
 557                        layer_info->v_zoom = ZOOM_X2;
 558                else if (v_scale == 4)
 559                        layer_info->v_zoom = ZOOM_X4;
 560                if (v_exp)
 561                        layer_info->h_exp = V_EXP_6_OVER_5;
 562        } else {
 563                /* no scaling, only cropping. Set display area to crop area */
 564                cfg->ysize = expected_ysize;
 565        }
 566        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 567                "crop display xsize = %d, ysize = %d\n",
 568                cfg->xsize, cfg->ysize);
 569}
 570
 571static void vpbe_disp_adj_position(struct vpbe_display *disp_dev,
 572                        struct vpbe_layer *layer,
 573                        int top, int left)
 574{
 575        struct osd_layer_config *cfg = &layer->layer_info.config;
 576        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 577
 578        cfg->xpos = min((unsigned int)left,
 579                        vpbe_dev->current_timings.xres - cfg->xsize);
 580        cfg->ypos = min((unsigned int)top,
 581                        vpbe_dev->current_timings.yres - cfg->ysize);
 582
 583        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 584                "new xpos = %d, ypos = %d\n",
 585                cfg->xpos, cfg->ypos);
 586}
 587
 588static void vpbe_disp_check_window_params(struct vpbe_display *disp_dev,
 589                        struct v4l2_rect *c)
 590{
 591        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 592
 593        if ((c->width == 0) ||
 594          ((c->width + c->left) > vpbe_dev->current_timings.xres))
 595                c->width = vpbe_dev->current_timings.xres - c->left;
 596
 597        if ((c->height == 0) || ((c->height + c->top) >
 598          vpbe_dev->current_timings.yres))
 599                c->height = vpbe_dev->current_timings.yres - c->top;
 600
 601        /* window height must be even for interlaced display */
 602        if (vpbe_dev->current_timings.interlaced)
 603                c->height &= (~0x01);
 604
 605}
 606
 607/**
 608 * vpbe_try_format()
 609 * If user application provides width and height, and have bytesperline set
 610 * to zero, driver calculates bytesperline and sizeimage based on hardware
 611 * limits.
 612 */
 613static int vpbe_try_format(struct vpbe_display *disp_dev,
 614                        struct v4l2_pix_format *pixfmt, int check)
 615{
 616        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 617        int min_height = 1;
 618        int min_width = 32;
 619        int max_height;
 620        int max_width;
 621        int bpp;
 622
 623        if ((pixfmt->pixelformat != V4L2_PIX_FMT_UYVY) &&
 624            (pixfmt->pixelformat != V4L2_PIX_FMT_NV12))
 625                /* choose default as V4L2_PIX_FMT_UYVY */
 626                pixfmt->pixelformat = V4L2_PIX_FMT_UYVY;
 627
 628        /* Check the field format */
 629        if ((pixfmt->field != V4L2_FIELD_INTERLACED) &&
 630                (pixfmt->field != V4L2_FIELD_NONE)) {
 631                if (vpbe_dev->current_timings.interlaced)
 632                        pixfmt->field = V4L2_FIELD_INTERLACED;
 633                else
 634                        pixfmt->field = V4L2_FIELD_NONE;
 635        }
 636
 637        if (pixfmt->field == V4L2_FIELD_INTERLACED)
 638                min_height = 2;
 639
 640        if (pixfmt->pixelformat == V4L2_PIX_FMT_NV12)
 641                bpp = 1;
 642        else
 643                bpp = 2;
 644
 645        max_width = vpbe_dev->current_timings.xres;
 646        max_height = vpbe_dev->current_timings.yres;
 647
 648        min_width /= bpp;
 649
 650        if (!pixfmt->width || (pixfmt->width < min_width) ||
 651                (pixfmt->width > max_width)) {
 652                pixfmt->width = vpbe_dev->current_timings.xres;
 653        }
 654
 655        if (!pixfmt->height || (pixfmt->height  < min_height) ||
 656                (pixfmt->height  > max_height)) {
 657                pixfmt->height = vpbe_dev->current_timings.yres;
 658        }
 659
 660        if (pixfmt->bytesperline < (pixfmt->width * bpp))
 661                pixfmt->bytesperline = pixfmt->width * bpp;
 662
 663        /* Make the bytesperline 32 byte aligned */
 664        pixfmt->bytesperline = ((pixfmt->width * bpp + 31) & ~31);
 665
 666        if (pixfmt->pixelformat == V4L2_PIX_FMT_NV12)
 667                pixfmt->sizeimage = pixfmt->bytesperline * pixfmt->height +
 668                                (pixfmt->bytesperline * pixfmt->height >> 1);
 669        else
 670                pixfmt->sizeimage = pixfmt->bytesperline * pixfmt->height;
 671
 672        return 0;
 673}
 674
 675static int vpbe_display_g_priority(struct file *file, void *priv,
 676                                enum v4l2_priority *p)
 677{
 678        struct vpbe_fh *fh = file->private_data;
 679        struct vpbe_layer *layer = fh->layer;
 680
 681        *p = v4l2_prio_max(&layer->prio);
 682
 683        return 0;
 684}
 685
 686static int vpbe_display_s_priority(struct file *file, void *priv,
 687                                enum v4l2_priority p)
 688{
 689        struct vpbe_fh *fh = file->private_data;
 690        struct vpbe_layer *layer = fh->layer;
 691        int ret;
 692
 693        ret = v4l2_prio_change(&layer->prio, &fh->prio, p);
 694
 695        return ret;
 696}
 697
 698static int vpbe_display_querycap(struct file *file, void  *priv,
 699                               struct v4l2_capability *cap)
 700{
 701        struct vpbe_fh *fh = file->private_data;
 702        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 703
 704        cap->version = VPBE_DISPLAY_VERSION_CODE;
 705        cap->device_caps = V4L2_CAP_VIDEO_OUTPUT | V4L2_CAP_STREAMING;
 706        cap->capabilities = cap->device_caps | V4L2_CAP_DEVICE_CAPS;
 707        snprintf(cap->driver, sizeof(cap->driver), "%s",
 708                dev_name(vpbe_dev->pdev));
 709        snprintf(cap->bus_info, sizeof(cap->bus_info), "platform:%s",
 710                 dev_name(vpbe_dev->pdev));
 711        strlcpy(cap->card, vpbe_dev->cfg->module_name, sizeof(cap->card));
 712
 713        return 0;
 714}
 715
 716static int vpbe_display_s_crop(struct file *file, void *priv,
 717                             const struct v4l2_crop *crop)
 718{
 719        struct vpbe_fh *fh = file->private_data;
 720        struct vpbe_layer *layer = fh->layer;
 721        struct vpbe_display *disp_dev = fh->disp_dev;
 722        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 723        struct osd_layer_config *cfg = &layer->layer_info.config;
 724        struct osd_state *osd_device = disp_dev->osd_device;
 725        struct v4l2_rect rect = crop->c;
 726        int ret;
 727
 728        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 729                "VIDIOC_S_CROP, layer id = %d\n", layer->device_id);
 730
 731        if (crop->type != V4L2_BUF_TYPE_VIDEO_OUTPUT) {
 732                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buf type\n");
 733                return -EINVAL;
 734        }
 735
 736        if (rect.top < 0)
 737                rect.top = 0;
 738        if (rect.left < 0)
 739                rect.left = 0;
 740
 741        vpbe_disp_check_window_params(disp_dev, &rect);
 742
 743        osd_device->ops.get_layer_config(osd_device,
 744                        layer->layer_info.id, cfg);
 745
 746        vpbe_disp_calculate_scale_factor(disp_dev, layer,
 747                                        rect.width,
 748                                        rect.height);
 749        vpbe_disp_adj_position(disp_dev, layer, rect.top,
 750                                        rect.left);
 751        ret = osd_device->ops.set_layer_config(osd_device,
 752                                layer->layer_info.id, cfg);
 753        if (ret < 0) {
 754                v4l2_err(&vpbe_dev->v4l2_dev,
 755                        "Error in set layer config:\n");
 756                return -EINVAL;
 757        }
 758
 759        /* apply zooming and h or v expansion */
 760        osd_device->ops.set_zoom(osd_device,
 761                        layer->layer_info.id,
 762                        layer->layer_info.h_zoom,
 763                        layer->layer_info.v_zoom);
 764        ret = osd_device->ops.set_vid_expansion(osd_device,
 765                        layer->layer_info.h_exp,
 766                        layer->layer_info.v_exp);
 767        if (ret < 0) {
 768                v4l2_err(&vpbe_dev->v4l2_dev,
 769                "Error in set vid expansion:\n");
 770                return -EINVAL;
 771        }
 772
 773        if ((layer->layer_info.h_zoom != ZOOM_X1) ||
 774                (layer->layer_info.v_zoom != ZOOM_X1) ||
 775                (layer->layer_info.h_exp != H_EXP_OFF) ||
 776                (layer->layer_info.v_exp != V_EXP_OFF))
 777                /* Enable expansion filter */
 778                osd_device->ops.set_interpolation_filter(osd_device, 1);
 779        else
 780                osd_device->ops.set_interpolation_filter(osd_device, 0);
 781
 782        return 0;
 783}
 784
 785static int vpbe_display_g_crop(struct file *file, void *priv,
 786                             struct v4l2_crop *crop)
 787{
 788        struct vpbe_fh *fh = file->private_data;
 789        struct vpbe_layer *layer = fh->layer;
 790        struct osd_layer_config *cfg = &layer->layer_info.config;
 791        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 792        struct osd_state *osd_device = fh->disp_dev->osd_device;
 793        struct v4l2_rect *rect = &crop->c;
 794
 795        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 796                        "VIDIOC_G_CROP, layer id = %d\n",
 797                        layer->device_id);
 798
 799        if (crop->type != V4L2_BUF_TYPE_VIDEO_OUTPUT) {
 800                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buf type\n");
 801                return -EINVAL;
 802        }
 803        osd_device->ops.get_layer_config(osd_device,
 804                                layer->layer_info.id, cfg);
 805        rect->top = cfg->ypos;
 806        rect->left = cfg->xpos;
 807        rect->width = cfg->xsize;
 808        rect->height = cfg->ysize;
 809
 810        return 0;
 811}
 812
 813static int vpbe_display_cropcap(struct file *file, void *priv,
 814                              struct v4l2_cropcap *cropcap)
 815{
 816        struct vpbe_fh *fh = file->private_data;
 817        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 818
 819        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_CROPCAP ioctl\n");
 820
 821        cropcap->type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
 822        cropcap->bounds.left = 0;
 823        cropcap->bounds.top = 0;
 824        cropcap->bounds.width = vpbe_dev->current_timings.xres;
 825        cropcap->bounds.height = vpbe_dev->current_timings.yres;
 826        cropcap->pixelaspect = vpbe_dev->current_timings.aspect;
 827        cropcap->defrect = cropcap->bounds;
 828        return 0;
 829}
 830
 831static int vpbe_display_g_fmt(struct file *file, void *priv,
 832                                struct v4l2_format *fmt)
 833{
 834        struct vpbe_fh *fh = file->private_data;
 835        struct vpbe_layer *layer = fh->layer;
 836        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 837
 838        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 839                        "VIDIOC_G_FMT, layer id = %d\n",
 840                        layer->device_id);
 841
 842        /* If buffer type is video output */
 843        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != fmt->type) {
 844                v4l2_err(&vpbe_dev->v4l2_dev, "invalid type\n");
 845                return -EINVAL;
 846        }
 847        /* Fill in the information about format */
 848        fmt->fmt.pix = layer->pix_fmt;
 849
 850        return 0;
 851}
 852
 853static int vpbe_display_enum_fmt(struct file *file, void  *priv,
 854                                   struct v4l2_fmtdesc *fmt)
 855{
 856        struct vpbe_fh *fh = file->private_data;
 857        struct vpbe_layer *layer = fh->layer;
 858        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 859        unsigned int index = 0;
 860
 861        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 862                                "VIDIOC_ENUM_FMT, layer id = %d\n",
 863                                layer->device_id);
 864        if (fmt->index > 1) {
 865                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid format index\n");
 866                return -EINVAL;
 867        }
 868
 869        /* Fill in the information about format */
 870        index = fmt->index;
 871        memset(fmt, 0, sizeof(*fmt));
 872        fmt->index = index;
 873        fmt->type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
 874        if (index == 0) {
 875                strcpy(fmt->description, "YUV 4:2:2 - UYVY");
 876                fmt->pixelformat = V4L2_PIX_FMT_UYVY;
 877        } else {
 878                strcpy(fmt->description, "Y/CbCr 4:2:0");
 879                fmt->pixelformat = V4L2_PIX_FMT_NV12;
 880        }
 881
 882        return 0;
 883}
 884
 885static int vpbe_display_s_fmt(struct file *file, void *priv,
 886                                struct v4l2_format *fmt)
 887{
 888        struct vpbe_fh *fh = file->private_data;
 889        struct vpbe_layer *layer = fh->layer;
 890        struct vpbe_display *disp_dev = fh->disp_dev;
 891        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
 892        struct osd_layer_config *cfg  = &layer->layer_info.config;
 893        struct v4l2_pix_format *pixfmt = &fmt->fmt.pix;
 894        struct osd_state *osd_device = disp_dev->osd_device;
 895        int ret;
 896
 897        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
 898                        "VIDIOC_S_FMT, layer id = %d\n",
 899                        layer->device_id);
 900
 901        /* If streaming is started, return error */
 902        if (layer->started) {
 903                v4l2_err(&vpbe_dev->v4l2_dev, "Streaming is started\n");
 904                return -EBUSY;
 905        }
 906        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != fmt->type) {
 907                v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "invalid type\n");
 908                return -EINVAL;
 909        }
 910        /* Check for valid pixel format */
 911        ret = vpbe_try_format(disp_dev, pixfmt, 1);
 912        if (ret)
 913                return ret;
 914
 915        /* YUV420 is requested, check availability of the
 916        other video window */
 917
 918        layer->pix_fmt = *pixfmt;
 919        if (pixfmt->pixelformat == V4L2_PIX_FMT_NV12) {
 920                struct vpbe_layer *otherlayer;
 921
 922                otherlayer = _vpbe_display_get_other_win_layer(disp_dev, layer);
 923                /* if other layer is available, only
 924                 * claim it, do not configure it
 925                 */
 926                ret = osd_device->ops.request_layer(osd_device,
 927                                                    otherlayer->layer_info.id);
 928                if (ret < 0) {
 929                        v4l2_err(&vpbe_dev->v4l2_dev,
 930                                 "Display Manager failed to allocate layer\n");
 931                        return -EBUSY;
 932                }
 933        }
 934
 935        /* Get osd layer config */
 936        osd_device->ops.get_layer_config(osd_device,
 937                        layer->layer_info.id, cfg);
 938        /* Store the pixel format in the layer object */
 939        cfg->xsize = pixfmt->width;
 940        cfg->ysize = pixfmt->height;
 941        cfg->line_length = pixfmt->bytesperline;
 942        cfg->ypos = 0;
 943        cfg->xpos = 0;
 944        cfg->interlaced = vpbe_dev->current_timings.interlaced;
 945
 946        if (V4L2_PIX_FMT_UYVY == pixfmt->pixelformat)
 947                cfg->pixfmt = PIXFMT_YCBCRI;
 948
 949        /* Change of the default pixel format for both video windows */
 950        if (V4L2_PIX_FMT_NV12 == pixfmt->pixelformat) {
 951                struct vpbe_layer *otherlayer;
 952                cfg->pixfmt = PIXFMT_NV12;
 953                otherlayer = _vpbe_display_get_other_win_layer(disp_dev,
 954                                                                layer);
 955                otherlayer->layer_info.config.pixfmt = PIXFMT_NV12;
 956        }
 957
 958        /* Set the layer config in the osd window */
 959        ret = osd_device->ops.set_layer_config(osd_device,
 960                                layer->layer_info.id, cfg);
 961        if (ret < 0) {
 962                v4l2_err(&vpbe_dev->v4l2_dev,
 963                                "Error in S_FMT params:\n");
 964                return -EINVAL;
 965        }
 966
 967        /* Readback and fill the local copy of current pix format */
 968        osd_device->ops.get_layer_config(osd_device,
 969                        layer->layer_info.id, cfg);
 970
 971        return 0;
 972}
 973
 974static int vpbe_display_try_fmt(struct file *file, void *priv,
 975                                  struct v4l2_format *fmt)
 976{
 977        struct vpbe_fh *fh = file->private_data;
 978        struct vpbe_display *disp_dev = fh->disp_dev;
 979        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
 980        struct v4l2_pix_format *pixfmt = &fmt->fmt.pix;
 981
 982        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_TRY_FMT\n");
 983
 984        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != fmt->type) {
 985                v4l2_err(&vpbe_dev->v4l2_dev, "invalid type\n");
 986                return -EINVAL;
 987        }
 988
 989        /* Check for valid field format */
 990        return  vpbe_try_format(disp_dev, pixfmt, 0);
 991
 992}
 993
 994/**
 995 * vpbe_display_s_std - Set the given standard in the encoder
 996 *
 997 * Sets the standard if supported by the current encoder. Return the status.
 998 * 0 - success & -EINVAL on error
 999 */
1000static int vpbe_display_s_std(struct file *file, void *priv,
1001                                v4l2_std_id std_id)
1002{
1003        struct vpbe_fh *fh = priv;
1004        struct vpbe_layer *layer = fh->layer;
1005        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1006        int ret;
1007
1008        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_S_STD\n");
1009
1010        /* If streaming is started, return error */
1011        if (layer->started) {
1012                v4l2_err(&vpbe_dev->v4l2_dev, "Streaming is started\n");
1013                return -EBUSY;
1014        }
1015        if (NULL != vpbe_dev->ops.s_std) {
1016                ret = vpbe_dev->ops.s_std(vpbe_dev, std_id);
1017                if (ret) {
1018                        v4l2_err(&vpbe_dev->v4l2_dev,
1019                        "Failed to set standard for sub devices\n");
1020                        return -EINVAL;
1021                }
1022        } else {
1023                return -EINVAL;
1024        }
1025
1026        return 0;
1027}
1028
1029/**
1030 * vpbe_display_g_std - Get the standard in the current encoder
1031 *
1032 * Get the standard in the current encoder. Return the status. 0 - success
1033 * -EINVAL on error
1034 */
1035static int vpbe_display_g_std(struct file *file, void *priv,
1036                                v4l2_std_id *std_id)
1037{
1038        struct vpbe_fh *fh = priv;
1039        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1040
1041        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_G_STD\n");
1042
1043        /* Get the standard from the current encoder */
1044        if (vpbe_dev->current_timings.timings_type & VPBE_ENC_STD) {
1045                *std_id = vpbe_dev->current_timings.std_id;
1046                return 0;
1047        }
1048
1049        return -EINVAL;
1050}
1051
1052/**
1053 * vpbe_display_enum_output - enumerate outputs
1054 *
1055 * Enumerates the outputs available at the vpbe display
1056 * returns the status, -EINVAL if end of output list
1057 */
1058static int vpbe_display_enum_output(struct file *file, void *priv,
1059                                    struct v4l2_output *output)
1060{
1061        struct vpbe_fh *fh = priv;
1062        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1063        int ret;
1064
1065        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_ENUM_OUTPUT\n");
1066
1067        /* Enumerate outputs */
1068
1069        if (NULL == vpbe_dev->ops.enum_outputs)
1070                return -EINVAL;
1071
1072        ret = vpbe_dev->ops.enum_outputs(vpbe_dev, output);
1073        if (ret) {
1074                v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1075                        "Failed to enumerate outputs\n");
1076                return -EINVAL;
1077        }
1078
1079        return 0;
1080}
1081
1082/**
1083 * vpbe_display_s_output - Set output to
1084 * the output specified by the index
1085 */
1086static int vpbe_display_s_output(struct file *file, void *priv,
1087                                unsigned int i)
1088{
1089        struct vpbe_fh *fh = priv;
1090        struct vpbe_layer *layer = fh->layer;
1091        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1092        int ret;
1093
1094        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_S_OUTPUT\n");
1095        /* If streaming is started, return error */
1096        if (layer->started) {
1097                v4l2_err(&vpbe_dev->v4l2_dev, "Streaming is started\n");
1098                return -EBUSY;
1099        }
1100        if (NULL == vpbe_dev->ops.set_output)
1101                return -EINVAL;
1102
1103        ret = vpbe_dev->ops.set_output(vpbe_dev, i);
1104        if (ret) {
1105                v4l2_err(&vpbe_dev->v4l2_dev,
1106                        "Failed to set output for sub devices\n");
1107                return -EINVAL;
1108        }
1109
1110        return 0;
1111}
1112
1113/**
1114 * vpbe_display_g_output - Get output from subdevice
1115 * for a given by the index
1116 */
1117static int vpbe_display_g_output(struct file *file, void *priv,
1118                                unsigned int *i)
1119{
1120        struct vpbe_fh *fh = priv;
1121        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1122
1123        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_G_OUTPUT\n");
1124        /* Get the standard from the current encoder */
1125        *i = vpbe_dev->current_out_index;
1126
1127        return 0;
1128}
1129
1130/**
1131 * vpbe_display_enum_dv_timings - Enumerate the dv timings
1132 *
1133 * enum the timings in the current encoder. Return the status. 0 - success
1134 * -EINVAL on error
1135 */
1136static int
1137vpbe_display_enum_dv_timings(struct file *file, void *priv,
1138                        struct v4l2_enum_dv_timings *timings)
1139{
1140        struct vpbe_fh *fh = priv;
1141        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1142        int ret;
1143
1144        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_ENUM_DV_TIMINGS\n");
1145
1146        /* Enumerate outputs */
1147        if (NULL == vpbe_dev->ops.enum_dv_timings)
1148                return -EINVAL;
1149
1150        ret = vpbe_dev->ops.enum_dv_timings(vpbe_dev, timings);
1151        if (ret) {
1152                v4l2_err(&vpbe_dev->v4l2_dev,
1153                        "Failed to enumerate dv timings info\n");
1154                return -EINVAL;
1155        }
1156
1157        return 0;
1158}
1159
1160/**
1161 * vpbe_display_s_dv_timings - Set the dv timings
1162 *
1163 * Set the timings in the current encoder. Return the status. 0 - success
1164 * -EINVAL on error
1165 */
1166static int
1167vpbe_display_s_dv_timings(struct file *file, void *priv,
1168                                struct v4l2_dv_timings *timings)
1169{
1170        struct vpbe_fh *fh = priv;
1171        struct vpbe_layer *layer = fh->layer;
1172        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1173        int ret;
1174
1175        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_S_DV_TIMINGS\n");
1176
1177
1178        /* If streaming is started, return error */
1179        if (layer->started) {
1180                v4l2_err(&vpbe_dev->v4l2_dev, "Streaming is started\n");
1181                return -EBUSY;
1182        }
1183
1184        /* Set the given standard in the encoder */
1185        if (!vpbe_dev->ops.s_dv_timings)
1186                return -EINVAL;
1187
1188        ret = vpbe_dev->ops.s_dv_timings(vpbe_dev, timings);
1189        if (ret) {
1190                v4l2_err(&vpbe_dev->v4l2_dev,
1191                        "Failed to set the dv timings info\n");
1192                return -EINVAL;
1193        }
1194
1195        return 0;
1196}
1197
1198/**
1199 * vpbe_display_g_dv_timings - Set the dv timings
1200 *
1201 * Get the timings in the current encoder. Return the status. 0 - success
1202 * -EINVAL on error
1203 */
1204static int
1205vpbe_display_g_dv_timings(struct file *file, void *priv,
1206                                struct v4l2_dv_timings *dv_timings)
1207{
1208        struct vpbe_fh *fh = priv;
1209        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1210
1211        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_G_DV_TIMINGS\n");
1212
1213        /* Get the given standard in the encoder */
1214
1215        if (vpbe_dev->current_timings.timings_type &
1216                                VPBE_ENC_DV_TIMINGS) {
1217                *dv_timings = vpbe_dev->current_timings.dv_timings;
1218        } else {
1219                return -EINVAL;
1220        }
1221
1222        return 0;
1223}
1224
1225static int vpbe_display_streamoff(struct file *file, void *priv,
1226                                enum v4l2_buf_type buf_type)
1227{
1228        struct vpbe_fh *fh = file->private_data;
1229        struct vpbe_layer *layer = fh->layer;
1230        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1231        struct osd_state *osd_device = fh->disp_dev->osd_device;
1232        int ret;
1233
1234        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1235                        "VIDIOC_STREAMOFF,layer id = %d\n",
1236                        layer->device_id);
1237
1238        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != buf_type) {
1239                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buffer type\n");
1240                return -EINVAL;
1241        }
1242
1243        /* If io is allowed for this file handle, return error */
1244        if (!fh->io_allowed) {
1245                v4l2_err(&vpbe_dev->v4l2_dev, "No io_allowed\n");
1246                return -EACCES;
1247        }
1248
1249        /* If streaming is not started, return error */
1250        if (!layer->started) {
1251                v4l2_err(&vpbe_dev->v4l2_dev, "streaming not started in layer"
1252                        " id = %d\n", layer->device_id);
1253                return -EINVAL;
1254        }
1255
1256        osd_device->ops.disable_layer(osd_device,
1257                        layer->layer_info.id);
1258        layer->started = 0;
1259        ret = vb2_streamoff(&layer->buffer_queue, buf_type);
1260
1261        return ret;
1262}
1263
1264static int vpbe_display_streamon(struct file *file, void *priv,
1265                         enum v4l2_buf_type buf_type)
1266{
1267        struct vpbe_fh *fh = file->private_data;
1268        struct vpbe_layer *layer = fh->layer;
1269        struct vpbe_display *disp_dev = fh->disp_dev;
1270        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1271        struct osd_state *osd_device = disp_dev->osd_device;
1272        int ret;
1273
1274        osd_device->ops.disable_layer(osd_device,
1275                        layer->layer_info.id);
1276
1277        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "VIDIOC_STREAMON, layerid=%d\n",
1278                                                layer->device_id);
1279
1280        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != buf_type) {
1281                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buffer type\n");
1282                return -EINVAL;
1283        }
1284
1285        /* If file handle is not allowed IO, return error */
1286        if (!fh->io_allowed) {
1287                v4l2_err(&vpbe_dev->v4l2_dev, "No io_allowed\n");
1288                return -EACCES;
1289        }
1290        /* If Streaming is already started, return error */
1291        if (layer->started) {
1292                v4l2_err(&vpbe_dev->v4l2_dev, "layer is already streaming\n");
1293                return -EBUSY;
1294        }
1295
1296        /*
1297         * Call vb2_streamon to start streaming
1298         * in videobuf
1299         */
1300        ret = vb2_streamon(&layer->buffer_queue, buf_type);
1301        if (ret) {
1302                v4l2_err(&vpbe_dev->v4l2_dev,
1303                "error in vb2_streamon\n");
1304                return ret;
1305        }
1306        return ret;
1307}
1308
1309static int vpbe_display_dqbuf(struct file *file, void *priv,
1310                      struct v4l2_buffer *buf)
1311{
1312        struct vpbe_fh *fh = file->private_data;
1313        struct vpbe_layer *layer = fh->layer;
1314        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1315        int ret;
1316
1317        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1318                "VIDIOC_DQBUF, layer id = %d\n",
1319                layer->device_id);
1320
1321        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != buf->type) {
1322                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buffer type\n");
1323                return -EINVAL;
1324        }
1325        /* If this file handle is not allowed to do IO, return error */
1326        if (!fh->io_allowed) {
1327                v4l2_err(&vpbe_dev->v4l2_dev, "No io_allowed\n");
1328                return -EACCES;
1329        }
1330        if (file->f_flags & O_NONBLOCK)
1331                /* Call videobuf_dqbuf for non blocking mode */
1332                ret = vb2_dqbuf(&layer->buffer_queue, buf, 1);
1333        else
1334                /* Call videobuf_dqbuf for blocking mode */
1335                ret = vb2_dqbuf(&layer->buffer_queue, buf, 0);
1336
1337        return ret;
1338}
1339
1340static int vpbe_display_qbuf(struct file *file, void *priv,
1341                     struct v4l2_buffer *p)
1342{
1343        struct vpbe_fh *fh = file->private_data;
1344        struct vpbe_layer *layer = fh->layer;
1345        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1346
1347        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1348                "VIDIOC_QBUF, layer id = %d\n",
1349                layer->device_id);
1350
1351        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != p->type) {
1352                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buffer type\n");
1353                return -EINVAL;
1354        }
1355
1356        /* If this file handle is not allowed to do IO, return error */
1357        if (!fh->io_allowed) {
1358                v4l2_err(&vpbe_dev->v4l2_dev, "No io_allowed\n");
1359                return -EACCES;
1360        }
1361
1362        return vb2_qbuf(&layer->buffer_queue, p);
1363}
1364
1365static int vpbe_display_querybuf(struct file *file, void *priv,
1366                         struct v4l2_buffer *buf)
1367{
1368        struct vpbe_fh *fh = file->private_data;
1369        struct vpbe_layer *layer = fh->layer;
1370        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1371
1372        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1373                "VIDIOC_QUERYBUF, layer id = %d\n",
1374                layer->device_id);
1375
1376        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != buf->type) {
1377                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buffer type\n");
1378                return -EINVAL;
1379        }
1380        /* Call vb2_querybuf to get information */
1381        return vb2_querybuf(&layer->buffer_queue, buf);
1382}
1383
1384static int vpbe_display_reqbufs(struct file *file, void *priv,
1385                        struct v4l2_requestbuffers *req_buf)
1386{
1387        struct vpbe_fh *fh = file->private_data;
1388        struct vpbe_layer *layer = fh->layer;
1389        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1390        struct vb2_queue *q;
1391        int ret;
1392        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_display_reqbufs\n");
1393
1394        if (V4L2_BUF_TYPE_VIDEO_OUTPUT != req_buf->type) {
1395                v4l2_err(&vpbe_dev->v4l2_dev, "Invalid buffer type\n");
1396                return -EINVAL;
1397        }
1398
1399        /* If io users of the layer is not zero, return error */
1400        if (0 != layer->io_usrs) {
1401                v4l2_err(&vpbe_dev->v4l2_dev, "not IO user\n");
1402                return -EBUSY;
1403        }
1404        /* Initialize videobuf queue as per the buffer type */
1405        layer->alloc_ctx = vb2_dma_contig_init_ctx(vpbe_dev->pdev);
1406        if (IS_ERR(layer->alloc_ctx)) {
1407                v4l2_err(&vpbe_dev->v4l2_dev, "Failed to get the context\n");
1408                return PTR_ERR(layer->alloc_ctx);
1409        }
1410        q = &layer->buffer_queue;
1411        memset(q, 0, sizeof(*q));
1412        q->type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
1413        q->io_modes = VB2_MMAP | VB2_USERPTR;
1414        q->drv_priv = fh;
1415        q->ops = &video_qops;
1416        q->mem_ops = &vb2_dma_contig_memops;
1417        q->buf_struct_size = sizeof(struct vpbe_disp_buffer);
1418        q->timestamp_type = V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC;
1419
1420        ret = vb2_queue_init(q);
1421        if (ret) {
1422                v4l2_err(&vpbe_dev->v4l2_dev, "vb2_queue_init() failed\n");
1423                vb2_dma_contig_cleanup_ctx(layer->alloc_ctx);
1424                return ret;
1425        }
1426        /* Set io allowed member of file handle to TRUE */
1427        fh->io_allowed = 1;
1428        /* Increment io usrs member of layer object to 1 */
1429        layer->io_usrs = 1;
1430        /* Store type of memory requested in layer object */
1431        layer->memory = req_buf->memory;
1432        /* Initialize buffer queue */
1433        INIT_LIST_HEAD(&layer->dma_queue);
1434        /* Allocate buffers */
1435        return vb2_reqbufs(q, req_buf);
1436}
1437
1438/*
1439 * vpbe_display_mmap()
1440 * It is used to map kernel space buffers into user spaces
1441 */
1442static int vpbe_display_mmap(struct file *filep, struct vm_area_struct *vma)
1443{
1444        /* Get the layer object and file handle object */
1445        struct vpbe_fh *fh = filep->private_data;
1446        struct vpbe_layer *layer = fh->layer;
1447        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1448        int ret;
1449
1450        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_display_mmap\n");
1451
1452        if (mutex_lock_interruptible(&layer->opslock))
1453                return -ERESTARTSYS;
1454        ret = vb2_mmap(&layer->buffer_queue, vma);
1455        mutex_unlock(&layer->opslock);
1456        return ret;
1457}
1458
1459/* vpbe_display_poll(): It is used for select/poll system call
1460 */
1461static unsigned int vpbe_display_poll(struct file *filep, poll_table *wait)
1462{
1463        struct vpbe_fh *fh = filep->private_data;
1464        struct vpbe_layer *layer = fh->layer;
1465        struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev;
1466        unsigned int err = 0;
1467
1468        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_display_poll\n");
1469        if (layer->started) {
1470                mutex_lock(&layer->opslock);
1471                err = vb2_poll(&layer->buffer_queue, filep, wait);
1472                mutex_unlock(&layer->opslock);
1473        }
1474        return err;
1475}
1476
1477/*
1478 * vpbe_display_open()
1479 * It creates object of file handle structure and stores it in private_data
1480 * member of filepointer
1481 */
1482static int vpbe_display_open(struct file *file)
1483{
1484        struct vpbe_fh *fh = NULL;
1485        struct vpbe_layer *layer = video_drvdata(file);
1486        struct vpbe_display *disp_dev = layer->disp_dev;
1487        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
1488        struct osd_state *osd_device = disp_dev->osd_device;
1489        int err;
1490
1491        /* Allocate memory for the file handle object */
1492        fh = kmalloc(sizeof(struct vpbe_fh), GFP_KERNEL);
1493        if (fh == NULL) {
1494                v4l2_err(&vpbe_dev->v4l2_dev,
1495                        "unable to allocate memory for file handle object\n");
1496                return -ENOMEM;
1497        }
1498        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1499                        "vpbe display open plane = %d\n",
1500                        layer->device_id);
1501
1502        /* store pointer to fh in private_data member of filep */
1503        file->private_data = fh;
1504        fh->layer = layer;
1505        fh->disp_dev = disp_dev;
1506
1507        if (!layer->usrs) {
1508                if (mutex_lock_interruptible(&layer->opslock))
1509                        return -ERESTARTSYS;
1510                /* First claim the layer for this device */
1511                err = osd_device->ops.request_layer(osd_device,
1512                                                layer->layer_info.id);
1513                mutex_unlock(&layer->opslock);
1514                if (err < 0) {
1515                        /* Couldn't get layer */
1516                        v4l2_err(&vpbe_dev->v4l2_dev,
1517                                "Display Manager failed to allocate layer\n");
1518                        kfree(fh);
1519                        return -EINVAL;
1520                }
1521        }
1522        /* Increment layer usrs counter */
1523        layer->usrs++;
1524        /* Set io_allowed member to false */
1525        fh->io_allowed = 0;
1526        /* Initialize priority of this instance to default priority */
1527        fh->prio = V4L2_PRIORITY_UNSET;
1528        v4l2_prio_open(&layer->prio, &fh->prio);
1529        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev,
1530                        "vpbe display device opened successfully\n");
1531        return 0;
1532}
1533
1534/*
1535 * vpbe_display_release()
1536 * This function deletes buffer queue, frees the buffers and the davinci
1537 * display file * handle
1538 */
1539static int vpbe_display_release(struct file *file)
1540{
1541        /* Get the layer object and file handle object */
1542        struct vpbe_fh *fh = file->private_data;
1543        struct vpbe_layer *layer = fh->layer;
1544        struct osd_layer_config *cfg  = &layer->layer_info.config;
1545        struct vpbe_display *disp_dev = fh->disp_dev;
1546        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
1547        struct osd_state *osd_device = disp_dev->osd_device;
1548
1549        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_display_release\n");
1550
1551        mutex_lock(&layer->opslock);
1552        /* if this instance is doing IO */
1553        if (fh->io_allowed) {
1554                /* Reset io_usrs member of layer object */
1555                layer->io_usrs = 0;
1556
1557                osd_device->ops.disable_layer(osd_device,
1558                                layer->layer_info.id);
1559                layer->started = 0;
1560                /* Free buffers allocated */
1561                vb2_queue_release(&layer->buffer_queue);
1562                vb2_dma_contig_cleanup_ctx(&layer->buffer_queue);
1563        }
1564
1565        /* Decrement layer usrs counter */
1566        layer->usrs--;
1567        /* If this file handle has initialize encoder device, reset it */
1568        if (!layer->usrs) {
1569                if (cfg->pixfmt == PIXFMT_NV12) {
1570                        struct vpbe_layer *otherlayer;
1571                        otherlayer =
1572                        _vpbe_display_get_other_win_layer(disp_dev, layer);
1573                        osd_device->ops.disable_layer(osd_device,
1574                                        otherlayer->layer_info.id);
1575                        osd_device->ops.release_layer(osd_device,
1576                                        otherlayer->layer_info.id);
1577                }
1578                osd_device->ops.disable_layer(osd_device,
1579                                layer->layer_info.id);
1580                osd_device->ops.release_layer(osd_device,
1581                                layer->layer_info.id);
1582        }
1583        /* Close the priority */
1584        v4l2_prio_close(&layer->prio, fh->prio);
1585        file->private_data = NULL;
1586        mutex_unlock(&layer->opslock);
1587
1588        /* Free memory allocated to file handle object */
1589        kfree(fh);
1590
1591        disp_dev->cbcr_ofst = 0;
1592
1593        return 0;
1594}
1595
1596/* vpbe capture ioctl operations */
1597static const struct v4l2_ioctl_ops vpbe_ioctl_ops = {
1598        .vidioc_querycap         = vpbe_display_querycap,
1599        .vidioc_g_fmt_vid_out    = vpbe_display_g_fmt,
1600        .vidioc_enum_fmt_vid_out = vpbe_display_enum_fmt,
1601        .vidioc_s_fmt_vid_out    = vpbe_display_s_fmt,
1602        .vidioc_try_fmt_vid_out  = vpbe_display_try_fmt,
1603        .vidioc_reqbufs          = vpbe_display_reqbufs,
1604        .vidioc_querybuf         = vpbe_display_querybuf,
1605        .vidioc_qbuf             = vpbe_display_qbuf,
1606        .vidioc_dqbuf            = vpbe_display_dqbuf,
1607        .vidioc_streamon         = vpbe_display_streamon,
1608        .vidioc_streamoff        = vpbe_display_streamoff,
1609        .vidioc_cropcap          = vpbe_display_cropcap,
1610        .vidioc_g_crop           = vpbe_display_g_crop,
1611        .vidioc_s_crop           = vpbe_display_s_crop,
1612        .vidioc_g_priority       = vpbe_display_g_priority,
1613        .vidioc_s_priority       = vpbe_display_s_priority,
1614        .vidioc_s_std            = vpbe_display_s_std,
1615        .vidioc_g_std            = vpbe_display_g_std,
1616        .vidioc_enum_output      = vpbe_display_enum_output,
1617        .vidioc_s_output         = vpbe_display_s_output,
1618        .vidioc_g_output         = vpbe_display_g_output,
1619        .vidioc_s_dv_timings     = vpbe_display_s_dv_timings,
1620        .vidioc_g_dv_timings     = vpbe_display_g_dv_timings,
1621        .vidioc_enum_dv_timings  = vpbe_display_enum_dv_timings,
1622};
1623
1624static struct v4l2_file_operations vpbe_fops = {
1625        .owner = THIS_MODULE,
1626        .open = vpbe_display_open,
1627        .release = vpbe_display_release,
1628        .unlocked_ioctl = video_ioctl2,
1629        .mmap = vpbe_display_mmap,
1630        .poll = vpbe_display_poll
1631};
1632
1633static int vpbe_device_get(struct device *dev, void *data)
1634{
1635        struct platform_device *pdev = to_platform_device(dev);
1636        struct vpbe_display *vpbe_disp  = data;
1637
1638        if (strcmp("vpbe_controller", pdev->name) == 0)
1639                vpbe_disp->vpbe_dev = platform_get_drvdata(pdev);
1640
1641        if (strstr(pdev->name, "vpbe-osd") != NULL)
1642                vpbe_disp->osd_device = platform_get_drvdata(pdev);
1643
1644        return 0;
1645}
1646
1647static int init_vpbe_layer(int i, struct vpbe_display *disp_dev,
1648                           struct platform_device *pdev)
1649{
1650        struct vpbe_layer *vpbe_display_layer = NULL;
1651        struct video_device *vbd = NULL;
1652
1653        /* Allocate memory for four plane display objects */
1654
1655        disp_dev->dev[i] =
1656                kzalloc(sizeof(struct vpbe_layer), GFP_KERNEL);
1657
1658        /* If memory allocation fails, return error */
1659        if (!disp_dev->dev[i]) {
1660                printk(KERN_ERR "ran out of memory\n");
1661                return  -ENOMEM;
1662        }
1663        spin_lock_init(&disp_dev->dev[i]->irqlock);
1664        mutex_init(&disp_dev->dev[i]->opslock);
1665
1666        /* Get the pointer to the layer object */
1667        vpbe_display_layer = disp_dev->dev[i];
1668        vbd = &vpbe_display_layer->video_dev;
1669        /* Initialize field of video device */
1670        vbd->release    = video_device_release_empty;
1671        vbd->fops       = &vpbe_fops;
1672        vbd->ioctl_ops  = &vpbe_ioctl_ops;
1673        vbd->minor      = -1;
1674        vbd->v4l2_dev   = &disp_dev->vpbe_dev->v4l2_dev;
1675        vbd->lock       = &vpbe_display_layer->opslock;
1676        vbd->vfl_dir    = VFL_DIR_TX;
1677
1678        if (disp_dev->vpbe_dev->current_timings.timings_type &
1679                        VPBE_ENC_STD)
1680                vbd->tvnorms = (V4L2_STD_525_60 | V4L2_STD_625_50);
1681
1682        snprintf(vbd->name, sizeof(vbd->name),
1683                        "DaVinci_VPBE Display_DRIVER_V%d.%d.%d",
1684                        (VPBE_DISPLAY_VERSION_CODE >> 16) & 0xff,
1685                        (VPBE_DISPLAY_VERSION_CODE >> 8) & 0xff,
1686                        (VPBE_DISPLAY_VERSION_CODE) & 0xff);
1687
1688        vpbe_display_layer->device_id = i;
1689
1690        vpbe_display_layer->layer_info.id =
1691                ((i == VPBE_DISPLAY_DEVICE_0) ? WIN_VID0 : WIN_VID1);
1692
1693        /* Initialize prio member of layer object */
1694        v4l2_prio_init(&vpbe_display_layer->prio);
1695
1696        return 0;
1697}
1698
1699static int register_device(struct vpbe_layer *vpbe_display_layer,
1700                           struct vpbe_display *disp_dev,
1701                           struct platform_device *pdev)
1702{
1703        int err;
1704
1705        v4l2_info(&disp_dev->vpbe_dev->v4l2_dev,
1706                  "Trying to register VPBE display device.\n");
1707        v4l2_info(&disp_dev->vpbe_dev->v4l2_dev,
1708                  "layer=%x,layer->video_dev=%x\n",
1709                  (int)vpbe_display_layer,
1710                  (int)&vpbe_display_layer->video_dev);
1711
1712        err = video_register_device(&vpbe_display_layer->video_dev,
1713                                    VFL_TYPE_GRABBER,
1714                                    -1);
1715        if (err)
1716                return -ENODEV;
1717
1718        vpbe_display_layer->disp_dev = disp_dev;
1719        /* set the driver data in platform device */
1720        platform_set_drvdata(pdev, disp_dev);
1721        video_set_drvdata(&vpbe_display_layer->video_dev,
1722                          vpbe_display_layer);
1723
1724        return 0;
1725}
1726
1727
1728
1729/*
1730 * vpbe_display_probe()
1731 * This function creates device entries by register itself to the V4L2 driver
1732 * and initializes fields of each layer objects
1733 */
1734static int vpbe_display_probe(struct platform_device *pdev)
1735{
1736        struct vpbe_layer *vpbe_display_layer;
1737        struct vpbe_display *disp_dev;
1738        struct resource *res = NULL;
1739        int k;
1740        int i;
1741        int err;
1742        int irq;
1743
1744        printk(KERN_DEBUG "vpbe_display_probe\n");
1745        /* Allocate memory for vpbe_display */
1746        disp_dev = devm_kzalloc(&pdev->dev, sizeof(struct vpbe_display),
1747                                GFP_KERNEL);
1748        if (!disp_dev)
1749                return -ENOMEM;
1750
1751        spin_lock_init(&disp_dev->dma_queue_lock);
1752        /*
1753         * Scan all the platform devices to find the vpbe
1754         * controller device and get the vpbe_dev object
1755         */
1756        err = bus_for_each_dev(&platform_bus_type, NULL, disp_dev,
1757                        vpbe_device_get);
1758        if (err < 0)
1759                return err;
1760        /* Initialize the vpbe display controller */
1761        if (NULL != disp_dev->vpbe_dev->ops.initialize) {
1762                err = disp_dev->vpbe_dev->ops.initialize(&pdev->dev,
1763                                                         disp_dev->vpbe_dev);
1764                if (err) {
1765                        v4l2_err(&disp_dev->vpbe_dev->v4l2_dev,
1766                                        "Error initing vpbe\n");
1767                        err = -ENOMEM;
1768                        goto probe_out;
1769                }
1770        }
1771
1772        for (i = 0; i < VPBE_DISPLAY_MAX_DEVICES; i++) {
1773                if (init_vpbe_layer(i, disp_dev, pdev)) {
1774                        err = -ENODEV;
1775                        goto probe_out;
1776                }
1777        }
1778
1779        res = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
1780        if (!res) {
1781                v4l2_err(&disp_dev->vpbe_dev->v4l2_dev,
1782                         "Unable to get VENC interrupt resource\n");
1783                err = -ENODEV;
1784                goto probe_out;
1785        }
1786
1787        irq = res->start;
1788        err = devm_request_irq(&pdev->dev, irq, venc_isr, IRQF_DISABLED,
1789                               VPBE_DISPLAY_DRIVER, disp_dev);
1790        if (err) {
1791                v4l2_err(&disp_dev->vpbe_dev->v4l2_dev,
1792                                "Unable to request interrupt\n");
1793                goto probe_out;
1794        }
1795
1796        for (i = 0; i < VPBE_DISPLAY_MAX_DEVICES; i++) {
1797                if (register_device(disp_dev->dev[i], disp_dev, pdev)) {
1798                        err = -ENODEV;
1799                        goto probe_out;
1800                }
1801        }
1802
1803        printk(KERN_DEBUG "Successfully completed the probing of vpbe v4l2 device\n");
1804        return 0;
1805
1806probe_out:
1807        for (k = 0; k < VPBE_DISPLAY_MAX_DEVICES; k++) {
1808                /* Get the pointer to the layer object */
1809                vpbe_display_layer = disp_dev->dev[k];
1810                /* Unregister video device */
1811                if (vpbe_display_layer) {
1812                        video_unregister_device(
1813                                &vpbe_display_layer->video_dev);
1814                                kfree(disp_dev->dev[k]);
1815                }
1816        }
1817        return err;
1818}
1819
1820/*
1821 * vpbe_display_remove()
1822 * It un-register hardware layer from V4L2 driver
1823 */
1824static int vpbe_display_remove(struct platform_device *pdev)
1825{
1826        struct vpbe_layer *vpbe_display_layer;
1827        struct vpbe_display *disp_dev = platform_get_drvdata(pdev);
1828        struct vpbe_device *vpbe_dev = disp_dev->vpbe_dev;
1829        int i;
1830
1831        v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_display_remove\n");
1832
1833        /* deinitialize the vpbe display controller */
1834        if (NULL != vpbe_dev->ops.deinitialize)
1835                vpbe_dev->ops.deinitialize(&pdev->dev, vpbe_dev);
1836        /* un-register device */
1837        for (i = 0; i < VPBE_DISPLAY_MAX_DEVICES; i++) {
1838                /* Get the pointer to the layer object */
1839                vpbe_display_layer = disp_dev->dev[i];
1840                /* Unregister video device */
1841                video_unregister_device(&vpbe_display_layer->video_dev);
1842
1843        }
1844        for (i = 0; i < VPBE_DISPLAY_MAX_DEVICES; i++) {
1845                kfree(disp_dev->dev[i]);
1846                disp_dev->dev[i] = NULL;
1847        }
1848
1849        return 0;
1850}
1851
1852static struct platform_driver vpbe_display_driver = {
1853        .driver = {
1854                .name = VPBE_DISPLAY_DRIVER,
1855                .owner = THIS_MODULE,
1856                .bus = &platform_bus_type,
1857        },
1858        .probe = vpbe_display_probe,
1859        .remove = vpbe_display_remove,
1860};
1861
1862module_platform_driver(vpbe_display_driver);
1863
1864MODULE_DESCRIPTION("TI DM644x/DM355/DM365 VPBE Display controller");
1865MODULE_LICENSE("GPL");
1866MODULE_AUTHOR("Texas Instruments");
1867