]> asedeno.scripts.mit.edu Git - linux.git/blob - drivers/staging/media/davinci_vpfe/vpfe_mc_capture.c
Linux 5.3-rc4
[linux.git] / drivers / staging / media / davinci_vpfe / vpfe_mc_capture.c
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Copyright (C) 2012 Texas Instruments Inc
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License as
7  * published by the Free Software Foundation version 2.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * Contributors:
15  *      Manjunath Hadli <manjunath.hadli@ti.com>
16  *      Prabhakar Lad <prabhakar.lad@ti.com>
17  *
18  *
19  * Driver name : VPFE Capture driver
20  *    VPFE Capture driver allows applications to capture and stream video
21  *    frames on DaVinci SoCs (DM6446, DM355 etc) from a YUV source such as
22  *    TVP5146 or  Raw Bayer RGB image data from an image sensor
23  *    such as Microns' MT9T001, MT9T031 etc.
24  *
25  *    These SoCs have, in common, a Video Processing Subsystem (VPSS) that
26  *    consists of a Video Processing Front End (VPFE) for capturing
27  *    video/raw image data and Video Processing Back End (VPBE) for displaying
28  *    YUV data through an in-built analog encoder or Digital LCD port. This
29  *    driver is for capture through VPFE. A typical EVM using these SoCs have
30  *    following high level configuration.
31  *
32  *    decoder(TVP5146/          YUV/
33  *      MT9T001)   -->  Raw Bayer RGB ---> MUX -> VPFE (CCDC/ISIF)
34  *                      data input              |      |
35  *                                                      V      |
36  *                                                    SDRAM    |
37  *                                                             V
38  *                                                         Image Processor
39  *                                                             |
40  *                                                             V
41  *                                                           SDRAM
42  *    The data flow happens from a decoder connected to the VPFE over a
43  *    YUV embedded (BT.656/BT.1120) or separate sync or raw bayer rgb interface
44  *    and to the input of VPFE through an optional MUX (if more inputs are
45  *    to be interfaced on the EVM). The input data is first passed through
46  *    CCDC (CCD Controller, a.k.a Image Sensor Interface, ISIF). The CCDC
47  *    does very little or no processing on YUV data and does pre-process Raw
48  *    Bayer RGB data through modules such as Defect Pixel Correction (DFC)
49  *    Color Space Conversion (CSC), data gain/offset etc. After this, data
50  *    can be written to SDRAM or can be connected to the image processing
51  *    block such as IPIPE (on DM355/DM365 only).
52  *
53  *    Features supported
54  *              - MMAP IO
55  *              - USERPTR IO
56  *              - Capture using TVP5146 over BT.656
57  *              - Support for interfacing decoders using sub device model
58  *              - Work with DM365 or DM355 or DM6446 CCDC to do Raw Bayer
59  *                RGB/YUV data capture to SDRAM.
60  *              - Chaining of Image Processor
61  *              - SINGLE-SHOT mode
62  */
63
64 #include <linux/interrupt.h>
65 #include <linux/module.h>
66 #include <linux/slab.h>
67
68 #include "vpfe.h"
69 #include "vpfe_mc_capture.h"
70
71 static bool debug;
72 static bool interface;
73
74 module_param(interface, bool, 0444);
75 module_param(debug, bool, 0644);
76
77 /*
78  * VPFE capture can be used for capturing video such as from TVP5146 or TVP7002
79  * and for capture raw bayer data from camera sensors such as mt9p031. At this
80  * point there is problem in co-existence of mt9p031 and tvp5146 due to i2c
81  * address collision. So set the variable below from bootargs to do either video
82  * capture or camera capture.
83  * interface = 0 - video capture (from TVP514x or such),
84  * interface = 1 - Camera capture (from mt9p031 or such)
85  * Re-visit this when we fix the co-existence issue
86  */
87 MODULE_PARM_DESC(interface, "interface 0-1 (default:0)");
88 MODULE_PARM_DESC(debug, "Debug level 0-1");
89
90 MODULE_DESCRIPTION("VPFE Video for Linux Capture Driver");
91 MODULE_LICENSE("GPL");
92 MODULE_AUTHOR("Texas Instruments");
93
94 /* map mbus_fmt to pixelformat */
95 void mbus_to_pix(const struct v4l2_mbus_framefmt *mbus,
96                            struct v4l2_pix_format *pix)
97 {
98         switch (mbus->code) {
99         case MEDIA_BUS_FMT_UYVY8_2X8:
100                 pix->pixelformat = V4L2_PIX_FMT_UYVY;
101                 pix->bytesperline = pix->width * 2;
102                 break;
103
104         case MEDIA_BUS_FMT_YUYV8_2X8:
105                 pix->pixelformat = V4L2_PIX_FMT_YUYV;
106                 pix->bytesperline = pix->width * 2;
107                 break;
108
109         case MEDIA_BUS_FMT_YUYV10_1X20:
110                 pix->pixelformat = V4L2_PIX_FMT_UYVY;
111                 pix->bytesperline = pix->width * 2;
112                 break;
113
114         case MEDIA_BUS_FMT_SGRBG12_1X12:
115                 pix->pixelformat = V4L2_PIX_FMT_SBGGR16;
116                 pix->bytesperline = pix->width * 2;
117                 break;
118
119         case MEDIA_BUS_FMT_SGRBG10_DPCM8_1X8:
120                 pix->pixelformat = V4L2_PIX_FMT_SGRBG10DPCM8;
121                 pix->bytesperline = pix->width;
122                 break;
123
124         case MEDIA_BUS_FMT_SGRBG10_ALAW8_1X8:
125                 pix->pixelformat = V4L2_PIX_FMT_SGRBG10ALAW8;
126                 pix->bytesperline = pix->width;
127                 break;
128
129         case MEDIA_BUS_FMT_YDYUYDYV8_1X16:
130                 pix->pixelformat = V4L2_PIX_FMT_NV12;
131                 pix->bytesperline = pix->width;
132                 break;
133
134         case MEDIA_BUS_FMT_Y8_1X8:
135                 pix->pixelformat = V4L2_PIX_FMT_GREY;
136                 pix->bytesperline = pix->width;
137                 break;
138
139         case MEDIA_BUS_FMT_UV8_1X8:
140                 pix->pixelformat = V4L2_PIX_FMT_UV8;
141                 pix->bytesperline = pix->width;
142                 break;
143
144         default:
145                 pr_err("Invalid mbus code set\n");
146         }
147         /* pitch should be 32 bytes aligned */
148         pix->bytesperline = ALIGN(pix->bytesperline, 32);
149         if (pix->pixelformat == V4L2_PIX_FMT_NV12)
150                 pix->sizeimage = pix->bytesperline * pix->height +
151                                 ((pix->bytesperline * pix->height) >> 1);
152         else
153                 pix->sizeimage = pix->bytesperline * pix->height;
154 }
155
156 /* ISR for VINT0*/
157 static irqreturn_t vpfe_isr(int irq, void *dev_id)
158 {
159         struct vpfe_device *vpfe_dev = dev_id;
160
161         v4l2_dbg(1, debug, &vpfe_dev->v4l2_dev, "%s\n", __func__);
162         vpfe_isif_buffer_isr(&vpfe_dev->vpfe_isif);
163         vpfe_resizer_buffer_isr(&vpfe_dev->vpfe_resizer);
164         return IRQ_HANDLED;
165 }
166
167 /* vpfe_vdint1_isr() - isr handler for VINT1 interrupt */
168 static irqreturn_t vpfe_vdint1_isr(int irq, void *dev_id)
169 {
170         struct vpfe_device *vpfe_dev = dev_id;
171
172         v4l2_dbg(1, debug, &vpfe_dev->v4l2_dev, "%s\n", __func__);
173         vpfe_isif_vidint1_isr(&vpfe_dev->vpfe_isif);
174         return IRQ_HANDLED;
175 }
176
177 /* vpfe_imp_dma_isr() - ISR for ipipe dma completion */
178 static irqreturn_t vpfe_imp_dma_isr(int irq, void *dev_id)
179 {
180         struct vpfe_device *vpfe_dev = dev_id;
181
182         v4l2_dbg(1, debug, &vpfe_dev->v4l2_dev, "%s\n", __func__);
183         vpfe_ipipeif_ss_buffer_isr(&vpfe_dev->vpfe_ipipeif);
184         vpfe_resizer_dma_isr(&vpfe_dev->vpfe_resizer);
185         return IRQ_HANDLED;
186 }
187
188 /*
189  * vpfe_disable_clock() - Disable clocks for vpfe capture driver
190  * @vpfe_dev - ptr to vpfe capture device
191  *
192  * Disables clocks defined in vpfe configuration. The function
193  * assumes that at least one clock is to be defined which is
194  * true as of now.
195  */
196 static void vpfe_disable_clock(struct vpfe_device *vpfe_dev)
197 {
198         struct vpfe_config *vpfe_cfg = vpfe_dev->cfg;
199         int i;
200
201         for (i = 0; i < vpfe_cfg->num_clocks; i++) {
202                 clk_disable_unprepare(vpfe_dev->clks[i]);
203                 clk_put(vpfe_dev->clks[i]);
204         }
205         kzfree(vpfe_dev->clks);
206         v4l2_info(vpfe_dev->pdev->driver, "vpfe capture clocks disabled\n");
207 }
208
209 /*
210  * vpfe_enable_clock() - Enable clocks for vpfe capture driver
211  * @vpfe_dev - ptr to vpfe capture device
212  *
213  * Enables clocks defined in vpfe configuration. The function
214  * assumes that at least one clock is to be defined which is
215  * true as of now.
216  */
217 static int vpfe_enable_clock(struct vpfe_device *vpfe_dev)
218 {
219         struct vpfe_config *vpfe_cfg = vpfe_dev->cfg;
220         int ret = -EFAULT;
221         int i;
222
223         if (!vpfe_cfg->num_clocks)
224                 return 0;
225
226         vpfe_dev->clks = kcalloc(vpfe_cfg->num_clocks,
227                                  sizeof(*vpfe_dev->clks), GFP_KERNEL);
228         if (!vpfe_dev->clks)
229                 return -ENOMEM;
230
231         for (i = 0; i < vpfe_cfg->num_clocks; i++) {
232                 if (vpfe_cfg->clocks[i] == NULL) {
233                         v4l2_err(vpfe_dev->pdev->driver,
234                                 "clock %s is not defined in vpfe config\n",
235                                 vpfe_cfg->clocks[i]);
236                         goto out;
237                 }
238
239                 vpfe_dev->clks[i] =
240                                 clk_get(vpfe_dev->pdev, vpfe_cfg->clocks[i]);
241                 if (IS_ERR(vpfe_dev->clks[i])) {
242                         v4l2_err(vpfe_dev->pdev->driver,
243                                 "Failed to get clock %s\n",
244                                 vpfe_cfg->clocks[i]);
245                         goto out;
246                 }
247
248                 if (clk_prepare_enable(vpfe_dev->clks[i])) {
249                         v4l2_err(vpfe_dev->pdev->driver,
250                                 "vpfe clock %s not enabled\n",
251                                 vpfe_cfg->clocks[i]);
252                         goto out;
253                 }
254
255                 v4l2_info(vpfe_dev->pdev->driver, "vpss clock %s enabled",
256                           vpfe_cfg->clocks[i]);
257         }
258
259         return 0;
260 out:
261         for (i = 0; i < vpfe_cfg->num_clocks; i++)
262                 if (!IS_ERR(vpfe_dev->clks[i])) {
263                         clk_disable_unprepare(vpfe_dev->clks[i]);
264                         clk_put(vpfe_dev->clks[i]);
265                 }
266
267         v4l2_err(vpfe_dev->pdev->driver, "Failed to enable clocks\n");
268         kzfree(vpfe_dev->clks);
269
270         return ret;
271 }
272
273 /*
274  * vpfe_detach_irq() - Detach IRQs for vpfe capture driver
275  * @vpfe_dev - ptr to vpfe capture device
276  *
277  * Detach all IRQs defined in vpfe configuration.
278  */
279 static void vpfe_detach_irq(struct vpfe_device *vpfe_dev)
280 {
281         free_irq(vpfe_dev->ccdc_irq0, vpfe_dev);
282         free_irq(vpfe_dev->ccdc_irq1, vpfe_dev);
283         free_irq(vpfe_dev->imp_dma_irq, vpfe_dev);
284 }
285
286 /*
287  * vpfe_attach_irq() - Attach IRQs for vpfe capture driver
288  * @vpfe_dev - ptr to vpfe capture device
289  *
290  * Attach all IRQs defined in vpfe configuration.
291  */
292 static int vpfe_attach_irq(struct vpfe_device *vpfe_dev)
293 {
294         int ret;
295
296         ret = request_irq(vpfe_dev->ccdc_irq0, vpfe_isr, 0,
297                           "vpfe_capture0", vpfe_dev);
298         if (ret < 0) {
299                 v4l2_err(&vpfe_dev->v4l2_dev,
300                         "Error: requesting VINT0 interrupt\n");
301                 return ret;
302         }
303
304         ret = request_irq(vpfe_dev->ccdc_irq1, vpfe_vdint1_isr, 0,
305                           "vpfe_capture1", vpfe_dev);
306         if (ret < 0) {
307                 v4l2_err(&vpfe_dev->v4l2_dev,
308                         "Error: requesting VINT1 interrupt\n");
309                 free_irq(vpfe_dev->ccdc_irq0, vpfe_dev);
310                 return ret;
311         }
312
313         ret = request_irq(vpfe_dev->imp_dma_irq, vpfe_imp_dma_isr,
314                           0, "Imp_Sdram_Irq", vpfe_dev);
315         if (ret < 0) {
316                 v4l2_err(&vpfe_dev->v4l2_dev,
317                          "Error: requesting IMP IRQ interrupt\n");
318                 free_irq(vpfe_dev->ccdc_irq1, vpfe_dev);
319                 free_irq(vpfe_dev->ccdc_irq0, vpfe_dev);
320                 return ret;
321         }
322
323         return 0;
324 }
325
326 /*
327  * register_i2c_devices() - register all i2c v4l2 subdevs
328  * @vpfe_dev - ptr to vpfe capture device
329  *
330  * register all i2c v4l2 subdevs
331  */
332 static int register_i2c_devices(struct vpfe_device *vpfe_dev)
333 {
334         struct vpfe_ext_subdev_info *sdinfo;
335         struct vpfe_config *vpfe_cfg;
336         struct i2c_adapter *i2c_adap;
337         unsigned int num_subdevs;
338         int ret;
339         int i;
340         int k;
341
342         vpfe_cfg = vpfe_dev->cfg;
343         i2c_adap = i2c_get_adapter(1);
344         num_subdevs = vpfe_cfg->num_subdevs;
345         vpfe_dev->sd =
346                   kcalloc(num_subdevs, sizeof(struct v4l2_subdev *),
347                           GFP_KERNEL);
348         if (!vpfe_dev->sd)
349                 return -ENOMEM;
350
351         for (i = 0, k = 0; i < num_subdevs; i++) {
352                 sdinfo = &vpfe_cfg->sub_devs[i];
353                 /*
354                  * register subdevices based on interface setting. Currently
355                  * tvp5146 and mt9p031 cannot co-exists due to i2c address
356                  * conflicts. So only one of them is registered. Re-visit this
357                  * once we have support for i2c switch handling in i2c driver
358                  * framework
359                  */
360                 if (interface == sdinfo->is_camera) {
361                         /* setup input path */
362                         if (vpfe_cfg->setup_input &&
363                                 vpfe_cfg->setup_input(sdinfo->grp_id) < 0) {
364                                 ret = -EFAULT;
365                                 v4l2_info(&vpfe_dev->v4l2_dev,
366                                           "could not setup input for %s\n",
367                                                 sdinfo->module_name);
368                                 goto probe_sd_out;
369                         }
370                         /* Load up the subdevice */
371                         vpfe_dev->sd[k] =
372                                 v4l2_i2c_new_subdev_board(&vpfe_dev->v4l2_dev,
373                                                   i2c_adap, &sdinfo->board_info,
374                                                   NULL);
375                         if (vpfe_dev->sd[k]) {
376                                 v4l2_info(&vpfe_dev->v4l2_dev,
377                                                 "v4l2 sub device %s registered\n",
378                                                 sdinfo->module_name);
379
380                                 vpfe_dev->sd[k]->grp_id = sdinfo->grp_id;
381                                 k++;
382
383                                 sdinfo->registered = 1;
384                         }
385                 } else {
386                         v4l2_info(&vpfe_dev->v4l2_dev,
387                                   "v4l2 sub device %s is not registered\n",
388                                   sdinfo->module_name);
389                 }
390         }
391         vpfe_dev->num_ext_subdevs = k;
392
393         return 0;
394
395 probe_sd_out:
396         kzfree(vpfe_dev->sd);
397
398         return ret;
399 }
400
401 /*
402  * vpfe_register_entities() - register all v4l2 subdevs and media entities
403  * @vpfe_dev - ptr to vpfe capture device
404  *
405  * register all v4l2 subdevs, media entities, and creates links
406  * between entities
407  */
408 static int vpfe_register_entities(struct vpfe_device *vpfe_dev)
409 {
410         unsigned int flags = 0;
411         int ret;
412         int i;
413
414         /* register i2c devices first */
415         ret = register_i2c_devices(vpfe_dev);
416         if (ret)
417                 return ret;
418
419         /* register rest of the sub-devs */
420         ret = vpfe_isif_register_entities(&vpfe_dev->vpfe_isif,
421                                           &vpfe_dev->v4l2_dev);
422         if (ret)
423                 return ret;
424
425         ret = vpfe_ipipeif_register_entities(&vpfe_dev->vpfe_ipipeif,
426                                              &vpfe_dev->v4l2_dev);
427         if (ret)
428                 goto out_isif_register;
429
430         ret = vpfe_ipipe_register_entities(&vpfe_dev->vpfe_ipipe,
431                                            &vpfe_dev->v4l2_dev);
432         if (ret)
433                 goto out_ipipeif_register;
434
435         ret = vpfe_resizer_register_entities(&vpfe_dev->vpfe_resizer,
436                                              &vpfe_dev->v4l2_dev);
437         if (ret)
438                 goto out_ipipe_register;
439
440         /* create links now, starting with external(i2c) entities */
441         for (i = 0; i < vpfe_dev->num_ext_subdevs; i++)
442                 /*
443                  * if entity has no pads (ex: amplifier),
444                  * can't establish link
445                  */
446                 if (vpfe_dev->sd[i]->entity.num_pads) {
447                         ret = media_create_pad_link(&vpfe_dev->sd[i]->entity,
448                                 0, &vpfe_dev->vpfe_isif.subdev.entity,
449                                 0, flags);
450                         if (ret < 0)
451                                 goto out_resizer_register;
452                 }
453
454         ret = media_create_pad_link(&vpfe_dev->vpfe_isif.subdev.entity, 1,
455                                        &vpfe_dev->vpfe_ipipeif.subdev.entity,
456                                        0, flags);
457         if (ret < 0)
458                 goto out_resizer_register;
459
460         ret = media_create_pad_link(&vpfe_dev->vpfe_ipipeif.subdev.entity, 1,
461                                        &vpfe_dev->vpfe_ipipe.subdev.entity,
462                                        0, flags);
463         if (ret < 0)
464                 goto out_resizer_register;
465
466         ret = media_create_pad_link(&vpfe_dev->vpfe_ipipe.subdev.entity,
467                         1, &vpfe_dev->vpfe_resizer.crop_resizer.subdev.entity,
468                         0, flags);
469         if (ret < 0)
470                 goto out_resizer_register;
471
472         ret = media_create_pad_link(&vpfe_dev->vpfe_ipipeif.subdev.entity, 1,
473                         &vpfe_dev->vpfe_resizer.crop_resizer.subdev.entity,
474                         0, flags);
475         if (ret < 0)
476                 goto out_resizer_register;
477
478         ret = v4l2_device_register_subdev_nodes(&vpfe_dev->v4l2_dev);
479         if (ret < 0)
480                 goto out_resizer_register;
481
482         return 0;
483
484 out_resizer_register:
485         vpfe_resizer_unregister_entities(&vpfe_dev->vpfe_resizer);
486 out_ipipe_register:
487         vpfe_ipipe_unregister_entities(&vpfe_dev->vpfe_ipipe);
488 out_ipipeif_register:
489         vpfe_ipipeif_unregister_entities(&vpfe_dev->vpfe_ipipeif);
490 out_isif_register:
491         vpfe_isif_unregister_entities(&vpfe_dev->vpfe_isif);
492
493         return ret;
494 }
495
496 /*
497  * vpfe_unregister_entities() - unregister all v4l2 subdevs and media entities
498  * @vpfe_dev - ptr to vpfe capture device
499  *
500  * unregister all v4l2 subdevs and media entities
501  */
502 static void vpfe_unregister_entities(struct vpfe_device *vpfe_dev)
503 {
504         vpfe_isif_unregister_entities(&vpfe_dev->vpfe_isif);
505         vpfe_ipipeif_unregister_entities(&vpfe_dev->vpfe_ipipeif);
506         vpfe_ipipe_unregister_entities(&vpfe_dev->vpfe_ipipe);
507         vpfe_resizer_unregister_entities(&vpfe_dev->vpfe_resizer);
508 }
509
510 /*
511  * vpfe_cleanup_modules() - cleanup all non-i2c v4l2 subdevs
512  * @vpfe_dev - ptr to vpfe capture device
513  * @pdev - pointer to platform device
514  *
515  * cleanup all v4l2 subdevs
516  */
517 static void vpfe_cleanup_modules(struct vpfe_device *vpfe_dev,
518                                  struct platform_device *pdev)
519 {
520         vpfe_isif_cleanup(&vpfe_dev->vpfe_isif, pdev);
521         vpfe_ipipeif_cleanup(&vpfe_dev->vpfe_ipipeif, pdev);
522         vpfe_ipipe_cleanup(&vpfe_dev->vpfe_ipipe, pdev);
523         vpfe_resizer_cleanup(&vpfe_dev->vpfe_resizer, pdev);
524 }
525
526 /*
527  * vpfe_initialize_modules() - initialize all non-i2c v4l2 subdevs
528  * @vpfe_dev - ptr to vpfe capture device
529  * @pdev - pointer to platform device
530  *
531  * initialize all v4l2 subdevs and media entities
532  */
533 static int vpfe_initialize_modules(struct vpfe_device *vpfe_dev,
534                                    struct platform_device *pdev)
535 {
536         int ret;
537
538         ret = vpfe_isif_init(&vpfe_dev->vpfe_isif, pdev);
539         if (ret)
540                 return ret;
541
542         ret = vpfe_ipipeif_init(&vpfe_dev->vpfe_ipipeif, pdev);
543         if (ret)
544                 goto out_isif_init;
545
546         ret = vpfe_ipipe_init(&vpfe_dev->vpfe_ipipe, pdev);
547         if (ret)
548                 goto out_ipipeif_init;
549
550         ret = vpfe_resizer_init(&vpfe_dev->vpfe_resizer, pdev);
551         if (ret)
552                 goto out_ipipe_init;
553
554         return 0;
555
556 out_ipipe_init:
557         vpfe_ipipe_cleanup(&vpfe_dev->vpfe_ipipe, pdev);
558 out_ipipeif_init:
559         vpfe_ipipeif_cleanup(&vpfe_dev->vpfe_ipipeif, pdev);
560 out_isif_init:
561         vpfe_isif_cleanup(&vpfe_dev->vpfe_isif, pdev);
562
563         return ret;
564 }
565
566 /*
567  * vpfe_probe() : vpfe probe function
568  * @pdev: platform device pointer
569  *
570  * This function creates device entries by register itself to the V4L2 driver
571  * and initializes fields of each device objects
572  */
573 static int vpfe_probe(struct platform_device *pdev)
574 {
575         struct vpfe_device *vpfe_dev;
576         struct resource *res1;
577         int ret = -ENOMEM;
578
579         vpfe_dev = kzalloc(sizeof(*vpfe_dev), GFP_KERNEL);
580         if (!vpfe_dev)
581                 return ret;
582
583         if (pdev->dev.platform_data == NULL) {
584                 v4l2_err(pdev->dev.driver, "Unable to get vpfe config\n");
585                 ret = -ENOENT;
586                 goto probe_free_dev_mem;
587         }
588
589         vpfe_dev->cfg = pdev->dev.platform_data;
590         if (vpfe_dev->cfg->card_name == NULL ||
591                         vpfe_dev->cfg->sub_devs == NULL) {
592                 v4l2_err(pdev->dev.driver, "null ptr in vpfe_cfg\n");
593                 ret = -ENOENT;
594                 goto probe_free_dev_mem;
595         }
596
597         /* Get VINT0 irq resource */
598         res1 = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
599         if (!res1) {
600                 v4l2_err(pdev->dev.driver,
601                          "Unable to get interrupt for VINT0\n");
602                 ret = -ENOENT;
603                 goto probe_free_dev_mem;
604         }
605         vpfe_dev->ccdc_irq0 = res1->start;
606
607         /* Get VINT1 irq resource */
608         res1 = platform_get_resource(pdev, IORESOURCE_IRQ, 1);
609         if (!res1) {
610                 v4l2_err(pdev->dev.driver,
611                          "Unable to get interrupt for VINT1\n");
612                 ret = -ENOENT;
613                 goto probe_free_dev_mem;
614         }
615         vpfe_dev->ccdc_irq1 = res1->start;
616
617         /* Get DMA irq resource */
618         res1 = platform_get_resource(pdev, IORESOURCE_IRQ, 2);
619         if (!res1) {
620                 v4l2_err(pdev->dev.driver,
621                          "Unable to get interrupt for DMA\n");
622                 ret = -ENOENT;
623                 goto probe_free_dev_mem;
624         }
625         vpfe_dev->imp_dma_irq = res1->start;
626
627         vpfe_dev->pdev = &pdev->dev;
628
629         /* enable vpss clocks */
630         ret = vpfe_enable_clock(vpfe_dev);
631         if (ret)
632                 goto probe_free_dev_mem;
633
634         ret = vpfe_initialize_modules(vpfe_dev, pdev);
635         if (ret)
636                 goto probe_disable_clock;
637
638         vpfe_dev->media_dev.dev = vpfe_dev->pdev;
639         strscpy((char *)&vpfe_dev->media_dev.model, "davinci-media",
640                 sizeof(vpfe_dev->media_dev.model));
641
642         ret = media_device_register(&vpfe_dev->media_dev);
643         if (ret) {
644                 v4l2_err(pdev->dev.driver,
645                         "Unable to register media device.\n");
646                 goto probe_out_entities_cleanup;
647         }
648
649         vpfe_dev->v4l2_dev.mdev = &vpfe_dev->media_dev;
650         ret = v4l2_device_register(&pdev->dev, &vpfe_dev->v4l2_dev);
651         if (ret) {
652                 v4l2_err(pdev->dev.driver, "Unable to register v4l2 device.\n");
653                 goto probe_out_media_unregister;
654         }
655
656         v4l2_info(&vpfe_dev->v4l2_dev, "v4l2 device registered\n");
657         /* set the driver data in platform device */
658         platform_set_drvdata(pdev, vpfe_dev);
659         /* register subdevs/entities */
660         ret = vpfe_register_entities(vpfe_dev);
661         if (ret)
662                 goto probe_out_v4l2_unregister;
663
664         ret = vpfe_attach_irq(vpfe_dev);
665         if (ret)
666                 goto probe_out_entities_unregister;
667
668         return 0;
669
670 probe_out_entities_unregister:
671         vpfe_unregister_entities(vpfe_dev);
672         kzfree(vpfe_dev->sd);
673 probe_out_v4l2_unregister:
674         v4l2_device_unregister(&vpfe_dev->v4l2_dev);
675 probe_out_media_unregister:
676         media_device_unregister(&vpfe_dev->media_dev);
677 probe_out_entities_cleanup:
678         vpfe_cleanup_modules(vpfe_dev, pdev);
679 probe_disable_clock:
680         vpfe_disable_clock(vpfe_dev);
681 probe_free_dev_mem:
682         kzfree(vpfe_dev);
683
684         return ret;
685 }
686
687 /*
688  * vpfe_remove : This function un-registers device from V4L2 driver
689  */
690 static int vpfe_remove(struct platform_device *pdev)
691 {
692         struct vpfe_device *vpfe_dev = platform_get_drvdata(pdev);
693
694         v4l2_info(pdev->dev.driver, "%s\n", __func__);
695
696         kzfree(vpfe_dev->sd);
697         vpfe_detach_irq(vpfe_dev);
698         vpfe_unregister_entities(vpfe_dev);
699         vpfe_cleanup_modules(vpfe_dev, pdev);
700         v4l2_device_unregister(&vpfe_dev->v4l2_dev);
701         media_device_unregister(&vpfe_dev->media_dev);
702         vpfe_disable_clock(vpfe_dev);
703         kzfree(vpfe_dev);
704
705         return 0;
706 }
707
708 static struct platform_driver vpfe_driver = {
709         .driver = {
710                 .name = CAPTURE_DRV_NAME,
711         },
712         .probe = vpfe_probe,
713         .remove = vpfe_remove,
714 };
715
716 module_platform_driver(vpfe_driver);