linux/drivers/media/platform/davinci/vpbe.c
<<
>>
Prefs
   1/*
   2 * Copyright (C) 2010 Texas Instruments Inc
   3 *
   4 * This program is free software; you can redistribute it and/or modify
   5 * it under the terms of the GNU General Public License as published by
   6 * the Free Software Foundation version 2.
   7 *
   8 * This program is distributed in the hope that it will be useful,
   9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10 * 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/fs.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/io.h>
  23#include <linux/slab.h>
  24#include <linux/clk.h>
  25#include <linux/err.h>
  26
  27#include <media/v4l2-device.h>
  28#include <media/davinci/vpbe_types.h>
  29#include <media/davinci/vpbe.h>
  30#include <media/davinci/vpss.h>
  31#include <media/davinci/vpbe_venc.h>
  32
  33#define VPBE_DEFAULT_OUTPUT     "Composite"
  34#define VPBE_DEFAULT_MODE       "ntsc"
  35
  36static char *def_output = VPBE_DEFAULT_OUTPUT;
  37static char *def_mode = VPBE_DEFAULT_MODE;
  38static int debug;
  39
  40module_param(def_output, charp, S_IRUGO);
  41module_param(def_mode, charp, S_IRUGO);
  42module_param(debug, int, 0644);
  43
  44MODULE_PARM_DESC(def_output, "vpbe output name (default:Composite)");
  45MODULE_PARM_DESC(def_mode, "vpbe output mode name (default:ntsc");
  46MODULE_PARM_DESC(debug, "Debug level 0-1");
  47
  48MODULE_DESCRIPTION("TI DMXXX VPBE Display controller");
  49MODULE_LICENSE("GPL");
  50MODULE_AUTHOR("Texas Instruments");
  51
  52/**
  53 * vpbe_current_encoder_info - Get config info for current encoder
  54 * @vpbe_dev: vpbe device ptr
  55 *
  56 * Return ptr to current encoder config info
  57 */
  58static struct encoder_config_info*
  59vpbe_current_encoder_info(struct vpbe_device *vpbe_dev)
  60{
  61        struct vpbe_config *cfg = vpbe_dev->cfg;
  62        int index = vpbe_dev->current_sd_index;
  63
  64        return ((index == 0) ? &cfg->venc :
  65                                &cfg->ext_encoders[index-1]);
  66}
  67
  68/**
  69 * vpbe_find_encoder_sd_index - Given a name find encoder sd index
  70 *
  71 * @cfg: ptr to vpbe cfg
  72 * @index: index used by application
  73 *
  74 * Return sd index of the encoder
  75 */
  76static int vpbe_find_encoder_sd_index(struct vpbe_config *cfg,
  77                             int index)
  78{
  79        char *encoder_name = cfg->outputs[index].subdev_name;
  80        int i;
  81
  82        /* Venc is always first */
  83        if (!strcmp(encoder_name, cfg->venc.module_name))
  84                return 0;
  85
  86        for (i = 0; i < cfg->num_ext_encoders; i++) {
  87                if (!strcmp(encoder_name,
  88                     cfg->ext_encoders[i].module_name))
  89                        return i+1;
  90        }
  91
  92        return -EINVAL;
  93}
  94
  95/**
  96 * vpbe_enum_outputs - enumerate outputs
  97 * @vpbe_dev: vpbe device ptr
  98 * @output: ptr to v4l2_output structure
  99 *
 100 * Enumerates the outputs available at the vpbe display
 101 * returns the status, -EINVAL if end of output list
 102 */
 103static int vpbe_enum_outputs(struct vpbe_device *vpbe_dev,
 104                             struct v4l2_output *output)
 105{
 106        struct vpbe_config *cfg = vpbe_dev->cfg;
 107        int temp_index = output->index;
 108
 109        if (temp_index >= cfg->num_outputs)
 110                return -EINVAL;
 111
 112        *output = cfg->outputs[temp_index].output;
 113        output->index = temp_index;
 114
 115        return 0;
 116}
 117
 118static int vpbe_get_mode_info(struct vpbe_device *vpbe_dev, char *mode,
 119                              int output_index)
 120{
 121        struct vpbe_config *cfg = vpbe_dev->cfg;
 122        struct vpbe_enc_mode_info var;
 123        int curr_output = output_index;
 124        int i;
 125
 126        if (!mode)
 127                return -EINVAL;
 128
 129        for (i = 0; i < cfg->outputs[curr_output].num_modes; i++) {
 130                var = cfg->outputs[curr_output].modes[i];
 131                if (!strcmp(mode, var.name)) {
 132                        vpbe_dev->current_timings = var;
 133                        return 0;
 134                }
 135        }
 136
 137        return -EINVAL;
 138}
 139
 140static int vpbe_get_current_mode_info(struct vpbe_device *vpbe_dev,
 141                                      struct vpbe_enc_mode_info *mode_info)
 142{
 143        if (!mode_info)
 144                return -EINVAL;
 145
 146        *mode_info = vpbe_dev->current_timings;
 147
 148        return 0;
 149}
 150
 151/* Get std by std id */
 152static int vpbe_get_std_info(struct vpbe_device *vpbe_dev,
 153                             v4l2_std_id std_id)
 154{
 155        struct vpbe_config *cfg = vpbe_dev->cfg;
 156        struct vpbe_enc_mode_info var;
 157        int curr_output = vpbe_dev->current_out_index;
 158        int i;
 159
 160        for (i = 0; i < vpbe_dev->cfg->outputs[curr_output].num_modes; i++) {
 161                var = cfg->outputs[curr_output].modes[i];
 162                if ((var.timings_type & VPBE_ENC_STD) &&
 163                  (var.std_id & std_id)) {
 164                        vpbe_dev->current_timings = var;
 165                        return 0;
 166                }
 167        }
 168
 169        return -EINVAL;
 170}
 171
 172static int vpbe_get_std_info_by_name(struct vpbe_device *vpbe_dev,
 173                                char *std_name)
 174{
 175        struct vpbe_config *cfg = vpbe_dev->cfg;
 176        struct vpbe_enc_mode_info var;
 177        int curr_output = vpbe_dev->current_out_index;
 178        int i;
 179
 180        for (i = 0; i < vpbe_dev->cfg->outputs[curr_output].num_modes; i++) {
 181                var = cfg->outputs[curr_output].modes[i];
 182                if (!strcmp(var.name, std_name)) {
 183                        vpbe_dev->current_timings = var;
 184                        return 0;
 185                }
 186        }
 187
 188        return -EINVAL;
 189}
 190
 191/**
 192 * vpbe_set_output - Set output
 193 * @vpbe_dev: vpbe device ptr
 194 * @index: index of output
 195 *
 196 * Set vpbe output to the output specified by the index
 197 */
 198static int vpbe_set_output(struct vpbe_device *vpbe_dev, int index)
 199{
 200        struct encoder_config_info *curr_enc_info =
 201                        vpbe_current_encoder_info(vpbe_dev);
 202        struct vpbe_config *cfg = vpbe_dev->cfg;
 203        struct venc_platform_data *venc_device = vpbe_dev->venc_device;
 204        int enc_out_index;
 205        int sd_index;
 206        int ret;
 207
 208        if (index >= cfg->num_outputs)
 209                return -EINVAL;
 210
 211        mutex_lock(&vpbe_dev->lock);
 212
 213        sd_index = vpbe_dev->current_sd_index;
 214        enc_out_index = cfg->outputs[index].output.index;
 215        /*
 216         * Currently we switch the encoder based on output selected
 217         * by the application. If media controller is implemented later
 218         * there is will be an API added to setup_link between venc
 219         * and external encoder. So in that case below comparison always
 220         * match and encoder will not be switched. But if application
 221         * chose not to use media controller, then this provides current
 222         * way of switching encoder at the venc output.
 223         */
 224        if (strcmp(curr_enc_info->module_name,
 225                   cfg->outputs[index].subdev_name)) {
 226                /* Need to switch the encoder at the output */
 227                sd_index = vpbe_find_encoder_sd_index(cfg, index);
 228                if (sd_index < 0) {
 229                        ret = -EINVAL;
 230                        goto unlock;
 231                }
 232
 233                ret = venc_device->setup_if_config(cfg->outputs[index].if_params);
 234                if (ret)
 235                        goto unlock;
 236        }
 237
 238        /* Set output at the encoder */
 239        ret = v4l2_subdev_call(vpbe_dev->encoders[sd_index], video,
 240                                       s_routing, 0, enc_out_index, 0);
 241        if (ret)
 242                goto unlock;
 243
 244        /*
 245         * It is assumed that venc or external encoder will set a default
 246         * mode in the sub device. For external encoder or LCD pannel output,
 247         * we also need to set up the lcd port for the required mode. So setup
 248         * the lcd port for the default mode that is configured in the board
 249         * arch/arm/mach-davinci/board-dm355-evm.setup file for the external
 250         * encoder.
 251         */
 252        ret = vpbe_get_mode_info(vpbe_dev,
 253                                 cfg->outputs[index].default_mode, index);
 254        if (!ret) {
 255                struct osd_state *osd_device = vpbe_dev->osd_device;
 256
 257                osd_device->ops.set_left_margin(osd_device,
 258                        vpbe_dev->current_timings.left_margin);
 259                osd_device->ops.set_top_margin(osd_device,
 260                vpbe_dev->current_timings.upper_margin);
 261                vpbe_dev->current_sd_index = sd_index;
 262                vpbe_dev->current_out_index = index;
 263        }
 264unlock:
 265        mutex_unlock(&vpbe_dev->lock);
 266        return ret;
 267}
 268
 269static int vpbe_set_default_output(struct vpbe_device *vpbe_dev)
 270{
 271        struct vpbe_config *cfg = vpbe_dev->cfg;
 272        int i;
 273
 274        for (i = 0; i < cfg->num_outputs; i++) {
 275                if (!strcmp(def_output,
 276                            cfg->outputs[i].output.name)) {
 277                        int ret = vpbe_set_output(vpbe_dev, i);
 278
 279                        if (!ret)
 280                                vpbe_dev->current_out_index = i;
 281                        return ret;
 282                }
 283        }
 284        return 0;
 285}
 286
 287/**
 288 * vpbe_get_output - Get output
 289 * @vpbe_dev: vpbe device ptr
 290 *
 291 * return current vpbe output to the the index
 292 */
 293static unsigned int vpbe_get_output(struct vpbe_device *vpbe_dev)
 294{
 295        return vpbe_dev->current_out_index;
 296}
 297
 298/*
 299 * vpbe_s_dv_timings - Set the given preset timings in the encoder
 300 *
 301 * Sets the timings if supported by the current encoder. Return the status.
 302 * 0 - success & -EINVAL on error
 303 */
 304static int vpbe_s_dv_timings(struct vpbe_device *vpbe_dev,
 305                    struct v4l2_dv_timings *dv_timings)
 306{
 307        struct vpbe_config *cfg = vpbe_dev->cfg;
 308        int out_index = vpbe_dev->current_out_index;
 309        struct vpbe_output *output = &cfg->outputs[out_index];
 310        int sd_index = vpbe_dev->current_sd_index;
 311        int ret, i;
 312
 313
 314        if (!(cfg->outputs[out_index].output.capabilities &
 315            V4L2_OUT_CAP_DV_TIMINGS))
 316                return -ENODATA;
 317
 318        for (i = 0; i < output->num_modes; i++) {
 319                if (output->modes[i].timings_type == VPBE_ENC_DV_TIMINGS &&
 320                    !memcmp(&output->modes[i].dv_timings,
 321                                dv_timings, sizeof(*dv_timings)))
 322                        break;
 323        }
 324        if (i >= output->num_modes)
 325                return -EINVAL;
 326        vpbe_dev->current_timings = output->modes[i];
 327        mutex_lock(&vpbe_dev->lock);
 328
 329        ret = v4l2_subdev_call(vpbe_dev->encoders[sd_index], video,
 330                                        s_dv_timings, dv_timings);
 331        if (!ret && vpbe_dev->amp) {
 332                /* Call amplifier subdevice */
 333                ret = v4l2_subdev_call(vpbe_dev->amp, video,
 334                                s_dv_timings, dv_timings);
 335        }
 336        /* set the lcd controller output for the given mode */
 337        if (!ret) {
 338                struct osd_state *osd_device = vpbe_dev->osd_device;
 339
 340                osd_device->ops.set_left_margin(osd_device,
 341                vpbe_dev->current_timings.left_margin);
 342                osd_device->ops.set_top_margin(osd_device,
 343                vpbe_dev->current_timings.upper_margin);
 344        }
 345        mutex_unlock(&vpbe_dev->lock);
 346
 347        return ret;
 348}
 349
 350/*
 351 * vpbe_g_dv_timings - Get the timings in the current encoder
 352 *
 353 * Get the timings in the current encoder. Return the status. 0 - success
 354 * -EINVAL on error
 355 */
 356static int vpbe_g_dv_timings(struct vpbe_device *vpbe_dev,
 357                     struct v4l2_dv_timings *dv_timings)
 358{
 359        struct vpbe_config *cfg = vpbe_dev->cfg;
 360        int out_index = vpbe_dev->current_out_index;
 361
 362        if (!(cfg->outputs[out_index].output.capabilities &
 363                V4L2_OUT_CAP_DV_TIMINGS))
 364                return -ENODATA;
 365
 366        if (vpbe_dev->current_timings.timings_type &
 367          VPBE_ENC_DV_TIMINGS) {
 368                *dv_timings = vpbe_dev->current_timings.dv_timings;
 369                return 0;
 370        }
 371
 372        return -EINVAL;
 373}
 374
 375/*
 376 * vpbe_enum_dv_timings - Enumerate the dv timings in the current encoder
 377 *
 378 * Get the timings in the current encoder. Return the status. 0 - success
 379 * -EINVAL on error
 380 */
 381static int vpbe_enum_dv_timings(struct vpbe_device *vpbe_dev,
 382                         struct v4l2_enum_dv_timings *timings)
 383{
 384        struct vpbe_config *cfg = vpbe_dev->cfg;
 385        int out_index = vpbe_dev->current_out_index;
 386        struct vpbe_output *output = &cfg->outputs[out_index];
 387        int j = 0;
 388        int i;
 389
 390        if (!(output->output.capabilities & V4L2_OUT_CAP_DV_TIMINGS))
 391                return -ENODATA;
 392
 393        for (i = 0; i < output->num_modes; i++) {
 394                if (output->modes[i].timings_type == VPBE_ENC_DV_TIMINGS) {
 395                        if (j == timings->index)
 396                                break;
 397                        j++;
 398                }
 399        }
 400
 401        if (i == output->num_modes)
 402                return -EINVAL;
 403        timings->timings = output->modes[i].dv_timings;
 404        return 0;
 405}
 406
 407/*
 408 * vpbe_s_std - Set the given standard in the encoder
 409 *
 410 * Sets the standard if supported by the current encoder. Return the status.
 411 * 0 - success & -EINVAL on error
 412 */
 413static int vpbe_s_std(struct vpbe_device *vpbe_dev, v4l2_std_id std_id)
 414{
 415        struct vpbe_config *cfg = vpbe_dev->cfg;
 416        int out_index = vpbe_dev->current_out_index;
 417        int sd_index = vpbe_dev->current_sd_index;
 418        int ret;
 419
 420        if (!(cfg->outputs[out_index].output.capabilities &
 421                V4L2_OUT_CAP_STD))
 422                return -ENODATA;
 423
 424        ret = vpbe_get_std_info(vpbe_dev, std_id);
 425        if (ret)
 426                return ret;
 427
 428        mutex_lock(&vpbe_dev->lock);
 429
 430        ret = v4l2_subdev_call(vpbe_dev->encoders[sd_index], video,
 431                               s_std_output, std_id);
 432        /* set the lcd controller output for the given mode */
 433        if (!ret) {
 434                struct osd_state *osd_device = vpbe_dev->osd_device;
 435
 436                osd_device->ops.set_left_margin(osd_device,
 437                vpbe_dev->current_timings.left_margin);
 438                osd_device->ops.set_top_margin(osd_device,
 439                vpbe_dev->current_timings.upper_margin);
 440        }
 441        mutex_unlock(&vpbe_dev->lock);
 442
 443        return ret;
 444}
 445
 446/*
 447 * vpbe_g_std - Get the standard in the current encoder
 448 *
 449 * Get the standard in the current encoder. Return the status. 0 - success
 450 * -EINVAL on error
 451 */
 452static int vpbe_g_std(struct vpbe_device *vpbe_dev, v4l2_std_id *std_id)
 453{
 454        struct vpbe_enc_mode_info *cur_timings = &vpbe_dev->current_timings;
 455        struct vpbe_config *cfg = vpbe_dev->cfg;
 456        int out_index = vpbe_dev->current_out_index;
 457
 458        if (!(cfg->outputs[out_index].output.capabilities & V4L2_OUT_CAP_STD))
 459                return -ENODATA;
 460
 461        if (cur_timings->timings_type & VPBE_ENC_STD) {
 462                *std_id = cur_timings->std_id;
 463                return 0;
 464        }
 465
 466        return -EINVAL;
 467}
 468
 469/*
 470 * vpbe_set_mode - Set mode in the current encoder using mode info
 471 *
 472 * Use the mode string to decide what timings to set in the encoder
 473 * This is typically useful when fbset command is used to change the current
 474 * timings by specifying a string to indicate the timings.
 475 */
 476static int vpbe_set_mode(struct vpbe_device *vpbe_dev,
 477                         struct vpbe_enc_mode_info *mode_info)
 478{
 479        struct vpbe_enc_mode_info *preset_mode = NULL;
 480        struct vpbe_config *cfg = vpbe_dev->cfg;
 481        struct v4l2_dv_timings dv_timings;
 482        struct osd_state *osd_device;
 483        int out_index = vpbe_dev->current_out_index;
 484        int i;
 485
 486        if (!mode_info || !mode_info->name)
 487                return -EINVAL;
 488
 489        for (i = 0; i < cfg->outputs[out_index].num_modes; i++) {
 490                if (!strcmp(mode_info->name,
 491                     cfg->outputs[out_index].modes[i].name)) {
 492                        preset_mode = &cfg->outputs[out_index].modes[i];
 493                        /*
 494                         * it may be one of the 3 timings type. Check and
 495                         * invoke right API
 496                         */
 497                        if (preset_mode->timings_type & VPBE_ENC_STD)
 498                                return vpbe_s_std(vpbe_dev,
 499                                                 preset_mode->std_id);
 500                        if (preset_mode->timings_type &
 501                                                VPBE_ENC_DV_TIMINGS) {
 502                                dv_timings =
 503                                        preset_mode->dv_timings;
 504                                return vpbe_s_dv_timings(vpbe_dev, &dv_timings);
 505                        }
 506                }
 507        }
 508
 509        /* Only custom timing should reach here */
 510        if (!preset_mode)
 511                return -EINVAL;
 512
 513        mutex_lock(&vpbe_dev->lock);
 514
 515        osd_device = vpbe_dev->osd_device;
 516        vpbe_dev->current_timings = *preset_mode;
 517        osd_device->ops.set_left_margin(osd_device,
 518                vpbe_dev->current_timings.left_margin);
 519        osd_device->ops.set_top_margin(osd_device,
 520                vpbe_dev->current_timings.upper_margin);
 521
 522        mutex_unlock(&vpbe_dev->lock);
 523        return 0;
 524}
 525
 526static int vpbe_set_default_mode(struct vpbe_device *vpbe_dev)
 527{
 528        int ret;
 529
 530        ret = vpbe_get_std_info_by_name(vpbe_dev, def_mode);
 531        if (ret)
 532                return ret;
 533
 534        /* set the default mode in the encoder */
 535        return vpbe_set_mode(vpbe_dev, &vpbe_dev->current_timings);
 536}
 537
 538static int platform_device_get(struct device *dev, void *data)
 539{
 540        struct platform_device *pdev = to_platform_device(dev);
 541        struct vpbe_device *vpbe_dev = data;
 542
 543        if (strstr(pdev->name, "vpbe-osd"))
 544                vpbe_dev->osd_device = platform_get_drvdata(pdev);
 545        if (strstr(pdev->name, "vpbe-venc"))
 546                vpbe_dev->venc_device = dev_get_platdata(&pdev->dev);
 547
 548        return 0;
 549}
 550
 551/**
 552 * vpbe_initialize() - Initialize the vpbe display controller
 553 * @dev: Master and slave device ptr
 554 * @vpbe_dev: vpbe device ptr
 555 *
 556 * Master frame buffer device drivers calls this to initialize vpbe
 557 * display controller. This will then registers v4l2 device and the sub
 558 * devices and sets a current encoder sub device for display. v4l2 display
 559 * device driver is the master and frame buffer display device driver is
 560 * the slave. Frame buffer display driver checks the initialized during
 561 * probe and exit if not initialized. Returns status.
 562 */
 563static int vpbe_initialize(struct device *dev, struct vpbe_device *vpbe_dev)
 564{
 565        struct encoder_config_info *enc_info;
 566        struct amp_config_info *amp_info;
 567        struct v4l2_subdev **enc_subdev;
 568        struct osd_state *osd_device;
 569        struct i2c_adapter *i2c_adap;
 570        int num_encoders;
 571        int ret = 0;
 572        int err;
 573        int i;
 574
 575        /*
 576         * v4l2 abd FBDev frame buffer devices will get the vpbe_dev pointer
 577         * from the platform device by iteration of platform drivers and
 578         * matching with device name
 579         */
 580        if (!vpbe_dev || !dev) {
 581                printk(KERN_ERR "Null device pointers.\n");
 582                return -ENODEV;
 583        }
 584
 585        if (vpbe_dev->initialized)
 586                return 0;
 587
 588        mutex_lock(&vpbe_dev->lock);
 589
 590        if (strcmp(vpbe_dev->cfg->module_name, "dm644x-vpbe-display") != 0) {
 591                /* We have dac clock available for platform */
 592                vpbe_dev->dac_clk = clk_get(vpbe_dev->pdev, "vpss_dac");
 593                if (IS_ERR(vpbe_dev->dac_clk)) {
 594                        ret =  PTR_ERR(vpbe_dev->dac_clk);
 595                        goto fail_mutex_unlock;
 596                }
 597                if (clk_prepare_enable(vpbe_dev->dac_clk)) {
 598                        ret =  -ENODEV;
 599                        clk_put(vpbe_dev->dac_clk);
 600                        goto fail_mutex_unlock;
 601                }
 602        }
 603
 604        /* first enable vpss clocks */
 605        vpss_enable_clock(VPSS_VPBE_CLOCK, 1);
 606
 607        /* First register a v4l2 device */
 608        ret = v4l2_device_register(dev, &vpbe_dev->v4l2_dev);
 609        if (ret) {
 610                v4l2_err(dev->driver,
 611                        "Unable to register v4l2 device.\n");
 612                goto fail_clk_put;
 613        }
 614        v4l2_info(&vpbe_dev->v4l2_dev, "vpbe v4l2 device registered\n");
 615
 616        err = bus_for_each_dev(&platform_bus_type, NULL, vpbe_dev,
 617                               platform_device_get);
 618        if (err < 0) {
 619                ret = err;
 620                goto fail_dev_unregister;
 621        }
 622
 623        vpbe_dev->venc = venc_sub_dev_init(&vpbe_dev->v4l2_dev,
 624                                           vpbe_dev->cfg->venc.module_name);
 625        /* register venc sub device */
 626        if (!vpbe_dev->venc) {
 627                v4l2_err(&vpbe_dev->v4l2_dev,
 628                        "vpbe unable to init venc sub device\n");
 629                ret = -ENODEV;
 630                goto fail_dev_unregister;
 631        }
 632        /* initialize osd device */
 633        osd_device = vpbe_dev->osd_device;
 634        if (osd_device->ops.initialize) {
 635                err = osd_device->ops.initialize(osd_device);
 636                if (err) {
 637                        v4l2_err(&vpbe_dev->v4l2_dev,
 638                                 "unable to initialize the OSD device");
 639                        err = -ENOMEM;
 640                        goto fail_dev_unregister;
 641                }
 642        }
 643
 644        /*
 645         * Register any external encoders that are configured. At index 0 we
 646         * store venc sd index.
 647         */
 648        num_encoders = vpbe_dev->cfg->num_ext_encoders + 1;
 649        vpbe_dev->encoders = kmalloc_array(num_encoders,
 650                                           sizeof(*vpbe_dev->encoders),
 651                                           GFP_KERNEL);
 652        if (!vpbe_dev->encoders) {
 653                ret = -ENOMEM;
 654                goto fail_dev_unregister;
 655        }
 656
 657        i2c_adap = i2c_get_adapter(vpbe_dev->cfg->i2c_adapter_id);
 658        for (i = 0; i < (vpbe_dev->cfg->num_ext_encoders + 1); i++) {
 659                if (i == 0) {
 660                        /* venc is at index 0 */
 661                        enc_subdev = &vpbe_dev->encoders[i];
 662                        *enc_subdev = vpbe_dev->venc;
 663                        continue;
 664                }
 665                enc_info = &vpbe_dev->cfg->ext_encoders[i];
 666                if (enc_info->is_i2c) {
 667                        enc_subdev = &vpbe_dev->encoders[i];
 668                        *enc_subdev = v4l2_i2c_new_subdev_board(
 669                                                &vpbe_dev->v4l2_dev, i2c_adap,
 670                                                &enc_info->board_info, NULL);
 671                        if (*enc_subdev)
 672                                v4l2_info(&vpbe_dev->v4l2_dev,
 673                                          "v4l2 sub device %s registered\n",
 674                                          enc_info->module_name);
 675                        else {
 676                                v4l2_err(&vpbe_dev->v4l2_dev, "encoder %s failed to register",
 677                                         enc_info->module_name);
 678                                ret = -ENODEV;
 679                                goto fail_kfree_encoders;
 680                        }
 681                } else
 682                        v4l2_warn(&vpbe_dev->v4l2_dev, "non-i2c encoders currently not supported");
 683        }
 684        /* Add amplifier subdevice for dm365 */
 685        if ((strcmp(vpbe_dev->cfg->module_name, "dm365-vpbe-display") == 0) &&
 686           vpbe_dev->cfg->amp) {
 687                amp_info = vpbe_dev->cfg->amp;
 688                if (amp_info->is_i2c) {
 689                        vpbe_dev->amp = v4l2_i2c_new_subdev_board(
 690                        &vpbe_dev->v4l2_dev, i2c_adap,
 691                        &amp_info->board_info, NULL);
 692                        if (!vpbe_dev->amp) {
 693                                v4l2_err(&vpbe_dev->v4l2_dev,
 694                                         "amplifier %s failed to register",
 695                                         amp_info->module_name);
 696                                ret = -ENODEV;
 697                                goto fail_kfree_encoders;
 698                        }
 699                        v4l2_info(&vpbe_dev->v4l2_dev,
 700                                          "v4l2 sub device %s registered\n",
 701                                          amp_info->module_name);
 702                } else {
 703                            vpbe_dev->amp = NULL;
 704                            v4l2_warn(&vpbe_dev->v4l2_dev, "non-i2c amplifiers currently not supported");
 705                }
 706        } else {
 707            vpbe_dev->amp = NULL;
 708        }
 709
 710        /* set the current encoder and output to that of venc by default */
 711        vpbe_dev->current_sd_index = 0;
 712        vpbe_dev->current_out_index = 0;
 713
 714        mutex_unlock(&vpbe_dev->lock);
 715
 716        printk(KERN_NOTICE "Setting default output to %s\n", def_output);
 717        ret = vpbe_set_default_output(vpbe_dev);
 718        if (ret) {
 719                v4l2_err(&vpbe_dev->v4l2_dev, "Failed to set default output %s",
 720                         def_output);
 721                goto fail_kfree_amp;
 722        }
 723
 724        printk(KERN_NOTICE "Setting default mode to %s\n", def_mode);
 725        ret = vpbe_set_default_mode(vpbe_dev);
 726        if (ret) {
 727                v4l2_err(&vpbe_dev->v4l2_dev, "Failed to set default mode %s",
 728                         def_mode);
 729                goto fail_kfree_amp;
 730        }
 731        vpbe_dev->initialized = 1;
 732        /* TBD handling of bootargs for default output and mode */
 733        return 0;
 734
 735fail_kfree_amp:
 736        mutex_lock(&vpbe_dev->lock);
 737        kfree(vpbe_dev->amp);
 738fail_kfree_encoders:
 739        kfree(vpbe_dev->encoders);
 740fail_dev_unregister:
 741        v4l2_device_unregister(&vpbe_dev->v4l2_dev);
 742fail_clk_put:
 743        if (strcmp(vpbe_dev->cfg->module_name, "dm644x-vpbe-display") != 0) {
 744                clk_disable_unprepare(vpbe_dev->dac_clk);
 745                clk_put(vpbe_dev->dac_clk);
 746        }
 747fail_mutex_unlock:
 748        mutex_unlock(&vpbe_dev->lock);
 749        return ret;
 750}
 751
 752/**
 753 * vpbe_deinitialize() - de-initialize the vpbe display controller
 754 * @dev: Master and slave device ptr
 755 * @vpbe_dev: vpbe device ptr
 756 *
 757 * vpbe_master and slave frame buffer devices calls this to de-initialize
 758 * the display controller. It is called when master and slave device
 759 * driver modules are removed and no longer requires the display controller.
 760 */
 761static void vpbe_deinitialize(struct device *dev, struct vpbe_device *vpbe_dev)
 762{
 763        v4l2_device_unregister(&vpbe_dev->v4l2_dev);
 764        if (strcmp(vpbe_dev->cfg->module_name, "dm644x-vpbe-display") != 0) {
 765                clk_disable_unprepare(vpbe_dev->dac_clk);
 766                clk_put(vpbe_dev->dac_clk);
 767        }
 768
 769        kfree(vpbe_dev->amp);
 770        kfree(vpbe_dev->encoders);
 771        vpbe_dev->initialized = 0;
 772        /* disable vpss clocks */
 773        vpss_enable_clock(VPSS_VPBE_CLOCK, 0);
 774}
 775
 776static const struct vpbe_device_ops vpbe_dev_ops = {
 777        .enum_outputs = vpbe_enum_outputs,
 778        .set_output = vpbe_set_output,
 779        .get_output = vpbe_get_output,
 780        .s_dv_timings = vpbe_s_dv_timings,
 781        .g_dv_timings = vpbe_g_dv_timings,
 782        .enum_dv_timings = vpbe_enum_dv_timings,
 783        .s_std = vpbe_s_std,
 784        .g_std = vpbe_g_std,
 785        .initialize = vpbe_initialize,
 786        .deinitialize = vpbe_deinitialize,
 787        .get_mode_info = vpbe_get_current_mode_info,
 788        .set_mode = vpbe_set_mode,
 789};
 790
 791static int vpbe_probe(struct platform_device *pdev)
 792{
 793        struct vpbe_device *vpbe_dev;
 794        struct vpbe_config *cfg;
 795
 796        if (!pdev->dev.platform_data) {
 797                v4l2_err(pdev->dev.driver, "No platform data\n");
 798                return -ENODEV;
 799        }
 800        cfg = pdev->dev.platform_data;
 801
 802        if (!cfg->module_name[0] ||
 803            !cfg->osd.module_name[0] ||
 804            !cfg->venc.module_name[0]) {
 805                v4l2_err(pdev->dev.driver, "vpbe display module names not defined\n");
 806                return -EINVAL;
 807        }
 808
 809        vpbe_dev = kzalloc(sizeof(*vpbe_dev), GFP_KERNEL);
 810        if (!vpbe_dev)
 811                return -ENOMEM;
 812
 813        vpbe_dev->cfg = cfg;
 814        vpbe_dev->ops = vpbe_dev_ops;
 815        vpbe_dev->pdev = &pdev->dev;
 816
 817        if (cfg->outputs->num_modes > 0)
 818                vpbe_dev->current_timings = vpbe_dev->cfg->outputs[0].modes[0];
 819        else {
 820                kfree(vpbe_dev);
 821                return -ENODEV;
 822        }
 823
 824        /* set the driver data in platform device */
 825        platform_set_drvdata(pdev, vpbe_dev);
 826        mutex_init(&vpbe_dev->lock);
 827
 828        return 0;
 829}
 830
 831static int vpbe_remove(struct platform_device *device)
 832{
 833        struct vpbe_device *vpbe_dev = platform_get_drvdata(device);
 834
 835        kfree(vpbe_dev);
 836
 837        return 0;
 838}
 839
 840static struct platform_driver vpbe_driver = {
 841        .driver = {
 842                .name   = "vpbe_controller",
 843        },
 844        .probe = vpbe_probe,
 845        .remove = vpbe_remove,
 846};
 847
 848module_platform_driver(vpbe_driver);
 849