linux/drivers/staging/vc04_services/bcm2835-camera/bcm2835-camera.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0
   2/*
   3 * Broadcom BM2835 V4L2 driver
   4 *
   5 * Copyright © 2013 Raspberry Pi (Trading) Ltd.
   6 *
   7 * Authors: Vincent Sanders @ Collabora
   8 *          Dave Stevenson @ Broadcom
   9 *              (now dave.stevenson@raspberrypi.org)
  10 *          Simon Mellor @ Broadcom
  11 *          Luke Diamand @ Broadcom
  12 */
  13
  14#include <linux/errno.h>
  15#include <linux/kernel.h>
  16#include <linux/module.h>
  17#include <linux/slab.h>
  18#include <media/videobuf2-vmalloc.h>
  19#include <media/videobuf2-dma-contig.h>
  20#include <media/v4l2-device.h>
  21#include <media/v4l2-ioctl.h>
  22#include <media/v4l2-ctrls.h>
  23#include <media/v4l2-fh.h>
  24#include <media/v4l2-event.h>
  25#include <media/v4l2-common.h>
  26#include <linux/delay.h>
  27#include <linux/platform_device.h>
  28
  29#include "mmal-common.h"
  30#include "mmal-encodings.h"
  31#include "mmal-vchiq.h"
  32#include "mmal-msg.h"
  33#include "mmal-parameters.h"
  34#include "bcm2835-camera.h"
  35
  36#define BM2835_MMAL_VERSION "0.0.2"
  37#define BM2835_MMAL_MODULE_NAME "bcm2835-v4l2"
  38#define MIN_WIDTH 32
  39#define MIN_HEIGHT 32
  40#define MIN_BUFFER_SIZE (80 * 1024)
  41
  42#define MAX_VIDEO_MODE_WIDTH 1280
  43#define MAX_VIDEO_MODE_HEIGHT 720
  44
  45#define MAX_BCM2835_CAMERAS 2
  46
  47int bcm2835_v4l2_debug;
  48module_param_named(debug, bcm2835_v4l2_debug, int, 0644);
  49MODULE_PARM_DESC(bcm2835_v4l2_debug, "Debug level 0-2");
  50
  51#define UNSET (-1)
  52static int video_nr[] = {[0 ... (MAX_BCM2835_CAMERAS - 1)] = UNSET };
  53module_param_array(video_nr, int, NULL, 0644);
  54MODULE_PARM_DESC(video_nr, "videoX start numbers, -1 is autodetect");
  55
  56static int max_video_width = MAX_VIDEO_MODE_WIDTH;
  57static int max_video_height = MAX_VIDEO_MODE_HEIGHT;
  58module_param(max_video_width, int, 0644);
  59MODULE_PARM_DESC(max_video_width, "Threshold for video mode");
  60module_param(max_video_height, int, 0644);
  61MODULE_PARM_DESC(max_video_height, "Threshold for video mode");
  62
  63/* global device data array */
  64static struct bm2835_mmal_dev *gdev[MAX_BCM2835_CAMERAS];
  65
  66#define FPS_MIN 1
  67#define FPS_MAX 90
  68
  69/* timeperframe: min/max and default */
  70static const struct v4l2_fract
  71        tpf_min     = {.numerator = 1,          .denominator = FPS_MAX},
  72        tpf_max     = {.numerator = 1,          .denominator = FPS_MIN},
  73        tpf_default = {.numerator = 1000,       .denominator = 30000};
  74
  75/* video formats */
  76static struct mmal_fmt formats[] = {
  77        {
  78                .fourcc = V4L2_PIX_FMT_YUV420,
  79                .mmal = MMAL_ENCODING_I420,
  80                .depth = 12,
  81                .mmal_component = COMP_CAMERA,
  82                .ybbp = 1,
  83                .remove_padding = 1,
  84        }, {
  85                .fourcc = V4L2_PIX_FMT_YUYV,
  86                .mmal = MMAL_ENCODING_YUYV,
  87                .depth = 16,
  88                .mmal_component = COMP_CAMERA,
  89                .ybbp = 2,
  90                .remove_padding = 0,
  91        }, {
  92                .fourcc = V4L2_PIX_FMT_RGB24,
  93                .mmal = MMAL_ENCODING_RGB24,
  94                .depth = 24,
  95                .mmal_component = COMP_CAMERA,
  96                .ybbp = 3,
  97                .remove_padding = 0,
  98        }, {
  99                .fourcc = V4L2_PIX_FMT_JPEG,
 100                .flags = V4L2_FMT_FLAG_COMPRESSED,
 101                .mmal = MMAL_ENCODING_JPEG,
 102                .depth = 8,
 103                .mmal_component = COMP_IMAGE_ENCODE,
 104                .ybbp = 0,
 105                .remove_padding = 0,
 106        }, {
 107                .fourcc = V4L2_PIX_FMT_H264,
 108                .flags = V4L2_FMT_FLAG_COMPRESSED,
 109                .mmal = MMAL_ENCODING_H264,
 110                .depth = 8,
 111                .mmal_component = COMP_VIDEO_ENCODE,
 112                .ybbp = 0,
 113                .remove_padding = 0,
 114        }, {
 115                .fourcc = V4L2_PIX_FMT_MJPEG,
 116                .flags = V4L2_FMT_FLAG_COMPRESSED,
 117                .mmal = MMAL_ENCODING_MJPEG,
 118                .depth = 8,
 119                .mmal_component = COMP_VIDEO_ENCODE,
 120                .ybbp = 0,
 121                .remove_padding = 0,
 122        }, {
 123                .fourcc = V4L2_PIX_FMT_YVYU,
 124                .mmal = MMAL_ENCODING_YVYU,
 125                .depth = 16,
 126                .mmal_component = COMP_CAMERA,
 127                .ybbp = 2,
 128                .remove_padding = 0,
 129        }, {
 130                .fourcc = V4L2_PIX_FMT_VYUY,
 131                .mmal = MMAL_ENCODING_VYUY,
 132                .depth = 16,
 133                .mmal_component = COMP_CAMERA,
 134                .ybbp = 2,
 135                .remove_padding = 0,
 136        }, {
 137                .fourcc = V4L2_PIX_FMT_UYVY,
 138                .mmal = MMAL_ENCODING_UYVY,
 139                .depth = 16,
 140                .mmal_component = COMP_CAMERA,
 141                .ybbp = 2,
 142                .remove_padding = 0,
 143        }, {
 144                .fourcc = V4L2_PIX_FMT_NV12,
 145                .mmal = MMAL_ENCODING_NV12,
 146                .depth = 12,
 147                .mmal_component = COMP_CAMERA,
 148                .ybbp = 1,
 149                .remove_padding = 1,
 150        }, {
 151                .fourcc = V4L2_PIX_FMT_BGR24,
 152                .mmal = MMAL_ENCODING_BGR24,
 153                .depth = 24,
 154                .mmal_component = COMP_CAMERA,
 155                .ybbp = 3,
 156                .remove_padding = 0,
 157        }, {
 158                .fourcc = V4L2_PIX_FMT_YVU420,
 159                .mmal = MMAL_ENCODING_YV12,
 160                .depth = 12,
 161                .mmal_component = COMP_CAMERA,
 162                .ybbp = 1,
 163                .remove_padding = 1,
 164        }, {
 165                .fourcc = V4L2_PIX_FMT_NV21,
 166                .mmal = MMAL_ENCODING_NV21,
 167                .depth = 12,
 168                .mmal_component = COMP_CAMERA,
 169                .ybbp = 1,
 170                .remove_padding = 1,
 171        }, {
 172                .fourcc = V4L2_PIX_FMT_BGR32,
 173                .mmal = MMAL_ENCODING_BGRA,
 174                .depth = 32,
 175                .mmal_component = COMP_CAMERA,
 176                .ybbp = 4,
 177                .remove_padding = 0,
 178        },
 179};
 180
 181static struct mmal_fmt *get_format(struct v4l2_format *f)
 182{
 183        struct mmal_fmt *fmt;
 184        unsigned int k;
 185
 186        for (k = 0; k < ARRAY_SIZE(formats); k++) {
 187                fmt = &formats[k];
 188                if (fmt->fourcc == f->fmt.pix.pixelformat)
 189                        return fmt;
 190        }
 191
 192        return NULL;
 193}
 194
 195/* ------------------------------------------------------------------
 196 *      Videobuf queue operations
 197 * ------------------------------------------------------------------
 198 */
 199
 200static int queue_setup(struct vb2_queue *vq,
 201                       unsigned int *nbuffers, unsigned int *nplanes,
 202                       unsigned int sizes[], struct device *alloc_ctxs[])
 203{
 204        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vq);
 205        unsigned long size;
 206
 207        /* refuse queue setup if port is not configured */
 208        if (!dev->capture.port) {
 209                v4l2_err(&dev->v4l2_dev,
 210                         "%s: capture port not configured\n", __func__);
 211                return -EINVAL;
 212        }
 213
 214        /* Handle CREATE_BUFS situation - *nplanes != 0 */
 215        if (*nplanes) {
 216                if (*nplanes != 1 ||
 217                    sizes[0] < dev->capture.port->current_buffer.size) {
 218                        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 219                                 "%s: dev:%p Invalid buffer request from CREATE_BUFS, size %u < %u, nplanes %u != 1\n",
 220                                 __func__, dev, sizes[0],
 221                                 dev->capture.port->current_buffer.size,
 222                                 *nplanes);
 223                        return -EINVAL;
 224                } else {
 225                        return 0;
 226                }
 227        }
 228
 229        /* Handle REQBUFS situation */
 230        size = dev->capture.port->current_buffer.size;
 231        if (size == 0) {
 232                v4l2_err(&dev->v4l2_dev,
 233                         "%s: capture port buffer size is zero\n", __func__);
 234                return -EINVAL;
 235        }
 236
 237        if (*nbuffers < dev->capture.port->minimum_buffer.num)
 238                *nbuffers = dev->capture.port->minimum_buffer.num;
 239
 240        dev->capture.port->current_buffer.num = *nbuffers;
 241
 242        *nplanes = 1;
 243
 244        sizes[0] = size;
 245
 246        /*
 247         * videobuf2-vmalloc allocator is context-less so no need to set
 248         * alloc_ctxs array.
 249         */
 250
 251        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p\n",
 252                 __func__, dev);
 253
 254        return 0;
 255}
 256
 257static int buffer_init(struct vb2_buffer *vb)
 258{
 259        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
 260        struct vb2_v4l2_buffer *vb2 = to_vb2_v4l2_buffer(vb);
 261        struct mmal_buffer *buf = container_of(vb2, struct mmal_buffer, vb);
 262
 263        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p, vb %p\n",
 264                 __func__, dev, vb);
 265        buf->buffer = vb2_plane_vaddr(&buf->vb.vb2_buf, 0);
 266        buf->buffer_size = vb2_plane_size(&buf->vb.vb2_buf, 0);
 267
 268        return mmal_vchi_buffer_init(dev->instance, buf);
 269}
 270
 271static int buffer_prepare(struct vb2_buffer *vb)
 272{
 273        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
 274        unsigned long size;
 275
 276        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p, vb %p\n",
 277                 __func__, dev, vb);
 278
 279        if (!dev->capture.port || !dev->capture.fmt)
 280                return -ENODEV;
 281
 282        size = dev->capture.stride * dev->capture.height;
 283        if (vb2_plane_size(vb, 0) < size) {
 284                v4l2_err(&dev->v4l2_dev,
 285                         "%s data will not fit into plane (%lu < %lu)\n",
 286                         __func__, vb2_plane_size(vb, 0), size);
 287                return -EINVAL;
 288        }
 289
 290        return 0;
 291}
 292
 293static void buffer_cleanup(struct vb2_buffer *vb)
 294{
 295        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
 296        struct vb2_v4l2_buffer *vb2 = to_vb2_v4l2_buffer(vb);
 297        struct mmal_buffer *buf = container_of(vb2, struct mmal_buffer, vb);
 298
 299        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p, vb %p\n",
 300                 __func__, dev, vb);
 301        mmal_vchi_buffer_cleanup(buf);
 302}
 303
 304static inline bool is_capturing(struct bm2835_mmal_dev *dev)
 305{
 306        return dev->capture.camera_port ==
 307            &dev->component[COMP_CAMERA]->output[CAM_PORT_CAPTURE];
 308}
 309
 310static void buffer_cb(struct vchiq_mmal_instance *instance,
 311                      struct vchiq_mmal_port *port,
 312                      int status,
 313                      struct mmal_buffer *buf,
 314                      unsigned long length, u32 mmal_flags, s64 dts, s64 pts)
 315{
 316        struct bm2835_mmal_dev *dev = port->cb_ctx;
 317
 318        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 319                 "%s: status:%d, buf:%p, length:%lu, flags %u, pts %lld\n",
 320                 __func__, status, buf, length, mmal_flags, pts);
 321
 322        if (status) {
 323                /* error in transfer */
 324                if (buf) {
 325                        /* there was a buffer with the error so return it */
 326                        vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_ERROR);
 327                }
 328                return;
 329        }
 330
 331        if (length == 0) {
 332                /* stream ended */
 333                if (dev->capture.frame_count) {
 334                        /* empty buffer whilst capturing - expected to be an
 335                         * EOS, so grab another frame
 336                         */
 337                        if (is_capturing(dev)) {
 338                                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 339                                         "Grab another frame");
 340                                vchiq_mmal_port_parameter_set(
 341                                        instance,
 342                                        dev->capture.camera_port,
 343                                        MMAL_PARAMETER_CAPTURE,
 344                                        &dev->capture.frame_count,
 345                                        sizeof(dev->capture.frame_count));
 346                        }
 347                        if (vchiq_mmal_submit_buffer(instance, port, buf))
 348                                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 349                                         "Failed to return EOS buffer");
 350                } else {
 351                        /* stopping streaming.
 352                         * return buffer, and signal frame completion
 353                         */
 354                        vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_ERROR);
 355                        complete(&dev->capture.frame_cmplt);
 356                }
 357                return;
 358        }
 359
 360        if (!dev->capture.frame_count) {
 361                /* signal frame completion */
 362                vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_ERROR);
 363                complete(&dev->capture.frame_cmplt);
 364                return;
 365        }
 366
 367        if (dev->capture.vc_start_timestamp != -1 && pts) {
 368                ktime_t timestamp;
 369                s64 runtime_us = pts -
 370                    dev->capture.vc_start_timestamp;
 371                timestamp = ktime_add_us(dev->capture.kernel_start_ts,
 372                                         runtime_us);
 373                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 374                         "Convert start time %llu and %llu with offset %llu to %llu\n",
 375                         ktime_to_ns(dev->capture.kernel_start_ts),
 376                         dev->capture.vc_start_timestamp, pts,
 377                         ktime_to_ns(timestamp));
 378                buf->vb.vb2_buf.timestamp = ktime_to_ns(timestamp);
 379        } else {
 380                buf->vb.vb2_buf.timestamp = ktime_get_ns();
 381        }
 382        buf->vb.sequence = dev->capture.sequence++;
 383        buf->vb.field = V4L2_FIELD_NONE;
 384
 385        vb2_set_plane_payload(&buf->vb.vb2_buf, 0, length);
 386        if (mmal_flags & MMAL_BUFFER_HEADER_FLAG_KEYFRAME)
 387                buf->vb.flags |= V4L2_BUF_FLAG_KEYFRAME;
 388
 389        vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_DONE);
 390
 391        if (mmal_flags & MMAL_BUFFER_HEADER_FLAG_EOS &&
 392            is_capturing(dev)) {
 393                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 394                         "Grab another frame as buffer has EOS");
 395                vchiq_mmal_port_parameter_set(
 396                        instance,
 397                        dev->capture.camera_port,
 398                        MMAL_PARAMETER_CAPTURE,
 399                        &dev->capture.frame_count,
 400                        sizeof(dev->capture.frame_count));
 401        }
 402}
 403
 404static int enable_camera(struct bm2835_mmal_dev *dev)
 405{
 406        int ret;
 407
 408        if (!dev->camera_use_count) {
 409                ret = vchiq_mmal_port_parameter_set(
 410                        dev->instance,
 411                        &dev->component[COMP_CAMERA]->control,
 412                        MMAL_PARAMETER_CAMERA_NUM, &dev->camera_num,
 413                        sizeof(dev->camera_num));
 414                if (ret < 0) {
 415                        v4l2_err(&dev->v4l2_dev,
 416                                 "Failed setting camera num, ret %d\n", ret);
 417                        return -EINVAL;
 418                }
 419
 420                ret = vchiq_mmal_component_enable(
 421                                dev->instance,
 422                                dev->component[COMP_CAMERA]);
 423                if (ret < 0) {
 424                        v4l2_err(&dev->v4l2_dev,
 425                                 "Failed enabling camera, ret %d\n", ret);
 426                        return -EINVAL;
 427                }
 428        }
 429        dev->camera_use_count++;
 430        v4l2_dbg(1, bcm2835_v4l2_debug,
 431                 &dev->v4l2_dev, "enabled camera (refcount %d)\n",
 432                        dev->camera_use_count);
 433        return 0;
 434}
 435
 436static int disable_camera(struct bm2835_mmal_dev *dev)
 437{
 438        int ret;
 439
 440        if (!dev->camera_use_count) {
 441                v4l2_err(&dev->v4l2_dev,
 442                         "Disabled the camera when already disabled\n");
 443                return -EINVAL;
 444        }
 445        dev->camera_use_count--;
 446        if (!dev->camera_use_count) {
 447                unsigned int i = 0xFFFFFFFF;
 448
 449                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 450                         "Disabling camera\n");
 451                ret =
 452                    vchiq_mmal_component_disable(
 453                                dev->instance,
 454                                dev->component[COMP_CAMERA]);
 455                if (ret < 0) {
 456                        v4l2_err(&dev->v4l2_dev,
 457                                 "Failed disabling camera, ret %d\n", ret);
 458                        return -EINVAL;
 459                }
 460                vchiq_mmal_port_parameter_set(
 461                        dev->instance,
 462                        &dev->component[COMP_CAMERA]->control,
 463                        MMAL_PARAMETER_CAMERA_NUM, &i,
 464                        sizeof(i));
 465        }
 466        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 467                 "Camera refcount now %d\n", dev->camera_use_count);
 468        return 0;
 469}
 470
 471static void buffer_queue(struct vb2_buffer *vb)
 472{
 473        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vb->vb2_queue);
 474        struct vb2_v4l2_buffer *vb2 = to_vb2_v4l2_buffer(vb);
 475        struct mmal_buffer *buf = container_of(vb2, struct mmal_buffer, vb);
 476        int ret;
 477
 478        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 479                 "%s: dev:%p buf:%p, idx %u\n",
 480                 __func__, dev, buf, vb2->vb2_buf.index);
 481
 482        ret = vchiq_mmal_submit_buffer(dev->instance, dev->capture.port, buf);
 483        if (ret < 0)
 484                v4l2_err(&dev->v4l2_dev, "%s: error submitting buffer\n",
 485                         __func__);
 486}
 487
 488static int start_streaming(struct vb2_queue *vq, unsigned int count)
 489{
 490        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vq);
 491        int ret;
 492        u32 parameter_size;
 493
 494        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p\n",
 495                 __func__, dev);
 496
 497        /* ensure a format has actually been set */
 498        if (!dev->capture.port)
 499                return -EINVAL;
 500
 501        if (enable_camera(dev) < 0) {
 502                v4l2_err(&dev->v4l2_dev, "Failed to enable camera\n");
 503                return -EINVAL;
 504        }
 505
 506        /*init_completion(&dev->capture.frame_cmplt); */
 507
 508        /* enable frame capture */
 509        dev->capture.frame_count = 1;
 510
 511        /* reset sequence number */
 512        dev->capture.sequence = 0;
 513
 514        /* if the preview is not already running, wait for a few frames for AGC
 515         * to settle down.
 516         */
 517        if (!dev->component[COMP_PREVIEW]->enabled)
 518                msleep(300);
 519
 520        /* enable the connection from camera to encoder (if applicable) */
 521        if (dev->capture.camera_port != dev->capture.port &&
 522            dev->capture.camera_port) {
 523                ret = vchiq_mmal_port_enable(dev->instance,
 524                                             dev->capture.camera_port, NULL);
 525                if (ret) {
 526                        v4l2_err(&dev->v4l2_dev,
 527                                 "Failed to enable encode tunnel - error %d\n",
 528                                 ret);
 529                        return -1;
 530                }
 531        }
 532
 533        /* Get VC timestamp at this point in time */
 534        parameter_size = sizeof(dev->capture.vc_start_timestamp);
 535        if (vchiq_mmal_port_parameter_get(dev->instance,
 536                                          dev->capture.camera_port,
 537                                          MMAL_PARAMETER_SYSTEM_TIME,
 538                                          &dev->capture.vc_start_timestamp,
 539                                          &parameter_size)) {
 540                v4l2_err(&dev->v4l2_dev,
 541                         "Failed to get VC start time - update your VC f/w\n");
 542
 543                /* Flag to indicate just to rely on kernel timestamps */
 544                dev->capture.vc_start_timestamp = -1;
 545        } else {
 546                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 547                         "Start time %lld size %d\n",
 548                         dev->capture.vc_start_timestamp, parameter_size);
 549        }
 550
 551        dev->capture.kernel_start_ts = ktime_get();
 552
 553        /* enable the camera port */
 554        dev->capture.port->cb_ctx = dev;
 555        ret =
 556            vchiq_mmal_port_enable(dev->instance, dev->capture.port, buffer_cb);
 557        if (ret) {
 558                v4l2_err(&dev->v4l2_dev,
 559                         "Failed to enable capture port - error %d. Disabling camera port again\n",
 560                         ret);
 561
 562                vchiq_mmal_port_disable(dev->instance,
 563                                        dev->capture.camera_port);
 564                if (disable_camera(dev) < 0) {
 565                        v4l2_err(&dev->v4l2_dev, "Failed to disable camera\n");
 566                        return -EINVAL;
 567                }
 568                return -1;
 569        }
 570
 571        /* capture the first frame */
 572        vchiq_mmal_port_parameter_set(dev->instance,
 573                                      dev->capture.camera_port,
 574                                      MMAL_PARAMETER_CAPTURE,
 575                                      &dev->capture.frame_count,
 576                                      sizeof(dev->capture.frame_count));
 577        return 0;
 578}
 579
 580/* abort streaming and wait for last buffer */
 581static void stop_streaming(struct vb2_queue *vq)
 582{
 583        int ret;
 584        unsigned long timeout;
 585        struct bm2835_mmal_dev *dev = vb2_get_drv_priv(vq);
 586        struct vchiq_mmal_port *port = dev->capture.port;
 587
 588        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "%s: dev:%p\n",
 589                 __func__, dev);
 590
 591        init_completion(&dev->capture.frame_cmplt);
 592        dev->capture.frame_count = 0;
 593
 594        /* ensure a format has actually been set */
 595        if (!dev->capture.port) {
 596                v4l2_err(&dev->v4l2_dev,
 597                         "no capture port - stream not started?\n");
 598                return;
 599        }
 600
 601        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "stopping capturing\n");
 602
 603        /* stop capturing frames */
 604        vchiq_mmal_port_parameter_set(dev->instance,
 605                                      dev->capture.camera_port,
 606                                      MMAL_PARAMETER_CAPTURE,
 607                                      &dev->capture.frame_count,
 608                                      sizeof(dev->capture.frame_count));
 609
 610        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 611                 "disabling connection\n");
 612
 613        /* disable the connection from camera to encoder */
 614        ret = vchiq_mmal_port_disable(dev->instance, dev->capture.camera_port);
 615        if (!ret && dev->capture.camera_port != dev->capture.port) {
 616                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 617                         "disabling port\n");
 618                ret = vchiq_mmal_port_disable(dev->instance, dev->capture.port);
 619        } else if (dev->capture.camera_port != dev->capture.port) {
 620                v4l2_err(&dev->v4l2_dev, "port_disable failed, error %d\n",
 621                         ret);
 622        }
 623
 624        /* wait for all buffers to be returned */
 625        while (atomic_read(&port->buffers_with_vpu)) {
 626                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 627                         "%s: Waiting for buffers to be returned - %d outstanding\n",
 628                         __func__, atomic_read(&port->buffers_with_vpu));
 629                timeout = wait_for_completion_timeout(&dev->capture.frame_cmplt,
 630                                                      HZ);
 631                if (timeout == 0) {
 632                        v4l2_err(&dev->v4l2_dev, "%s: Timeout waiting for buffers to be returned - %d outstanding\n",
 633                                 __func__,
 634                                 atomic_read(&port->buffers_with_vpu));
 635                        break;
 636                }
 637        }
 638
 639        if (disable_camera(dev) < 0)
 640                v4l2_err(&dev->v4l2_dev, "Failed to disable camera\n");
 641}
 642
 643static const struct vb2_ops bm2835_mmal_video_qops = {
 644        .queue_setup = queue_setup,
 645        .buf_init = buffer_init,
 646        .buf_prepare = buffer_prepare,
 647        .buf_cleanup = buffer_cleanup,
 648        .buf_queue = buffer_queue,
 649        .start_streaming = start_streaming,
 650        .stop_streaming = stop_streaming,
 651        .wait_prepare = vb2_ops_wait_prepare,
 652        .wait_finish = vb2_ops_wait_finish,
 653};
 654
 655/* ------------------------------------------------------------------
 656 *      IOCTL operations
 657 * ------------------------------------------------------------------
 658 */
 659
 660static int set_overlay_params(struct bm2835_mmal_dev *dev,
 661                              struct vchiq_mmal_port *port)
 662{
 663        struct mmal_parameter_displayregion prev_config = {
 664                .set =  MMAL_DISPLAY_SET_LAYER |
 665                        MMAL_DISPLAY_SET_ALPHA |
 666                        MMAL_DISPLAY_SET_DEST_RECT |
 667                        MMAL_DISPLAY_SET_FULLSCREEN,
 668                .layer = PREVIEW_LAYER,
 669                .alpha = dev->overlay.global_alpha,
 670                .fullscreen = 0,
 671                .dest_rect = {
 672                        .x = dev->overlay.w.left,
 673                        .y = dev->overlay.w.top,
 674                        .width = dev->overlay.w.width,
 675                        .height = dev->overlay.w.height,
 676                },
 677        };
 678        return vchiq_mmal_port_parameter_set(dev->instance, port,
 679                                             MMAL_PARAMETER_DISPLAYREGION,
 680                                             &prev_config, sizeof(prev_config));
 681}
 682
 683/* overlay ioctl */
 684static int vidioc_enum_fmt_vid_overlay(struct file *file, void *priv,
 685                                       struct v4l2_fmtdesc *f)
 686{
 687        struct mmal_fmt *fmt;
 688
 689        if (f->index >= ARRAY_SIZE(formats))
 690                return -EINVAL;
 691
 692        fmt = &formats[f->index];
 693
 694        f->pixelformat = fmt->fourcc;
 695
 696        return 0;
 697}
 698
 699static int vidioc_g_fmt_vid_overlay(struct file *file, void *priv,
 700                                    struct v4l2_format *f)
 701{
 702        struct bm2835_mmal_dev *dev = video_drvdata(file);
 703
 704        f->fmt.win = dev->overlay;
 705
 706        return 0;
 707}
 708
 709static int vidioc_try_fmt_vid_overlay(struct file *file, void *priv,
 710                                      struct v4l2_format *f)
 711{
 712        struct bm2835_mmal_dev *dev = video_drvdata(file);
 713
 714        f->fmt.win.field = V4L2_FIELD_NONE;
 715        f->fmt.win.chromakey = 0;
 716        f->fmt.win.clips = NULL;
 717        f->fmt.win.clipcount = 0;
 718        f->fmt.win.bitmap = NULL;
 719
 720        v4l_bound_align_image(&f->fmt.win.w.width, MIN_WIDTH, dev->max_width, 1,
 721                              &f->fmt.win.w.height, MIN_HEIGHT, dev->max_height,
 722                              1, 0);
 723        v4l_bound_align_image(&f->fmt.win.w.left, MIN_WIDTH, dev->max_width, 1,
 724                              &f->fmt.win.w.top, MIN_HEIGHT, dev->max_height,
 725                              1, 0);
 726
 727        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 728                 "Overlay: Now w/h %dx%d l/t %dx%d\n",
 729                f->fmt.win.w.width, f->fmt.win.w.height,
 730                f->fmt.win.w.left, f->fmt.win.w.top);
 731
 732        v4l2_dump_win_format(1,
 733                             bcm2835_v4l2_debug,
 734                             &dev->v4l2_dev,
 735                             &f->fmt.win,
 736                             __func__);
 737        return 0;
 738}
 739
 740static int vidioc_s_fmt_vid_overlay(struct file *file, void *priv,
 741                                    struct v4l2_format *f)
 742{
 743        struct bm2835_mmal_dev *dev = video_drvdata(file);
 744
 745        vidioc_try_fmt_vid_overlay(file, priv, f);
 746
 747        dev->overlay = f->fmt.win;
 748        if (dev->component[COMP_PREVIEW]->enabled) {
 749                set_overlay_params(dev,
 750                                   &dev->component[COMP_PREVIEW]->input[0]);
 751        }
 752
 753        return 0;
 754}
 755
 756static int vidioc_overlay(struct file *file, void *f, unsigned int on)
 757{
 758        int ret;
 759        struct bm2835_mmal_dev *dev = video_drvdata(file);
 760        struct vchiq_mmal_port *src;
 761        struct vchiq_mmal_port *dst;
 762
 763        if ((on && dev->component[COMP_PREVIEW]->enabled) ||
 764            (!on && !dev->component[COMP_PREVIEW]->enabled))
 765                return 0;       /* already in requested state */
 766
 767        src =
 768            &dev->component[COMP_CAMERA]->output[CAM_PORT_PREVIEW];
 769
 770        if (!on) {
 771                /* disconnect preview ports and disable component */
 772                ret = vchiq_mmal_port_disable(dev->instance, src);
 773                if (!ret)
 774                        ret =
 775                            vchiq_mmal_port_connect_tunnel(dev->instance, src,
 776                                                           NULL);
 777                if (ret >= 0)
 778                        ret = vchiq_mmal_component_disable(
 779                                        dev->instance,
 780                                        dev->component[COMP_PREVIEW]);
 781
 782                disable_camera(dev);
 783                return ret;
 784        }
 785
 786        /* set preview port format and connect it to output */
 787        dst = &dev->component[COMP_PREVIEW]->input[0];
 788
 789        ret = vchiq_mmal_port_set_format(dev->instance, src);
 790        if (ret < 0)
 791                return ret;
 792
 793        ret = set_overlay_params(dev, dst);
 794        if (ret < 0)
 795                return ret;
 796
 797        if (enable_camera(dev) < 0)
 798                return -EINVAL;
 799
 800        ret = vchiq_mmal_component_enable(
 801                        dev->instance,
 802                        dev->component[COMP_PREVIEW]);
 803        if (ret < 0)
 804                return ret;
 805
 806        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev, "connecting %p to %p\n",
 807                 src, dst);
 808        ret = vchiq_mmal_port_connect_tunnel(dev->instance, src, dst);
 809        if (ret)
 810                return ret;
 811
 812        return vchiq_mmal_port_enable(dev->instance, src, NULL);
 813}
 814
 815static int vidioc_g_fbuf(struct file *file, void *fh,
 816                         struct v4l2_framebuffer *a)
 817{
 818        /* The video overlay must stay within the framebuffer and can't be
 819         * positioned independently.
 820         */
 821        struct bm2835_mmal_dev *dev = video_drvdata(file);
 822        struct vchiq_mmal_port *preview_port =
 823                &dev->component[COMP_CAMERA]->output[CAM_PORT_PREVIEW];
 824
 825        a->capability = V4L2_FBUF_CAP_EXTERNOVERLAY |
 826                        V4L2_FBUF_CAP_GLOBAL_ALPHA;
 827        a->flags = V4L2_FBUF_FLAG_OVERLAY;
 828        a->fmt.width = preview_port->es.video.width;
 829        a->fmt.height = preview_port->es.video.height;
 830        a->fmt.pixelformat = V4L2_PIX_FMT_YUV420;
 831        a->fmt.bytesperline = preview_port->es.video.width;
 832        a->fmt.sizeimage = (preview_port->es.video.width *
 833                               preview_port->es.video.height * 3) >> 1;
 834        a->fmt.colorspace = V4L2_COLORSPACE_SMPTE170M;
 835
 836        return 0;
 837}
 838
 839/* input ioctls */
 840static int vidioc_enum_input(struct file *file, void *priv,
 841                             struct v4l2_input *inp)
 842{
 843        /* only a single camera input */
 844        if (inp->index)
 845                return -EINVAL;
 846
 847        inp->type = V4L2_INPUT_TYPE_CAMERA;
 848        sprintf((char *)inp->name, "Camera %u", inp->index);
 849        return 0;
 850}
 851
 852static int vidioc_g_input(struct file *file, void *priv, unsigned int *i)
 853{
 854        *i = 0;
 855        return 0;
 856}
 857
 858static int vidioc_s_input(struct file *file, void *priv, unsigned int i)
 859{
 860        if (i)
 861                return -EINVAL;
 862
 863        return 0;
 864}
 865
 866/* capture ioctls */
 867static int vidioc_querycap(struct file *file, void *priv,
 868                           struct v4l2_capability *cap)
 869{
 870        struct bm2835_mmal_dev *dev = video_drvdata(file);
 871        u32 major;
 872        u32 minor;
 873
 874        vchiq_mmal_version(dev->instance, &major, &minor);
 875
 876        strcpy((char *)cap->driver, "bm2835 mmal");
 877        snprintf((char *)cap->card, sizeof(cap->card), "mmal service %d.%d",
 878                 major, minor);
 879
 880        snprintf((char *)cap->bus_info, sizeof(cap->bus_info),
 881                 "platform:%s", dev->v4l2_dev.name);
 882        return 0;
 883}
 884
 885static int vidioc_enum_fmt_vid_cap(struct file *file, void *priv,
 886                                   struct v4l2_fmtdesc *f)
 887{
 888        struct mmal_fmt *fmt;
 889
 890        if (f->index >= ARRAY_SIZE(formats))
 891                return -EINVAL;
 892
 893        fmt = &formats[f->index];
 894
 895        f->pixelformat = fmt->fourcc;
 896
 897        return 0;
 898}
 899
 900static int vidioc_g_fmt_vid_cap(struct file *file, void *priv,
 901                                struct v4l2_format *f)
 902{
 903        struct bm2835_mmal_dev *dev = video_drvdata(file);
 904
 905        f->fmt.pix.width = dev->capture.width;
 906        f->fmt.pix.height = dev->capture.height;
 907        f->fmt.pix.field = V4L2_FIELD_NONE;
 908        f->fmt.pix.pixelformat = dev->capture.fmt->fourcc;
 909        f->fmt.pix.bytesperline = dev->capture.stride;
 910        f->fmt.pix.sizeimage = dev->capture.buffersize;
 911
 912        if (dev->capture.fmt->fourcc == V4L2_PIX_FMT_RGB24)
 913                f->fmt.pix.colorspace = V4L2_COLORSPACE_SRGB;
 914        else if (dev->capture.fmt->fourcc == V4L2_PIX_FMT_JPEG)
 915                f->fmt.pix.colorspace = V4L2_COLORSPACE_JPEG;
 916        else
 917                f->fmt.pix.colorspace = V4L2_COLORSPACE_SMPTE170M;
 918        f->fmt.pix.priv = 0;
 919
 920        v4l2_dump_pix_format(1, bcm2835_v4l2_debug, &dev->v4l2_dev, &f->fmt.pix,
 921                             __func__);
 922        return 0;
 923}
 924
 925static int vidioc_try_fmt_vid_cap(struct file *file, void *priv,
 926                                  struct v4l2_format *f)
 927{
 928        struct bm2835_mmal_dev *dev = video_drvdata(file);
 929        struct mmal_fmt *mfmt;
 930
 931        mfmt = get_format(f);
 932        if (!mfmt) {
 933                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 934                         "Fourcc format (0x%08x) unknown.\n",
 935                         f->fmt.pix.pixelformat);
 936                f->fmt.pix.pixelformat = formats[0].fourcc;
 937                mfmt = get_format(f);
 938        }
 939
 940        f->fmt.pix.field = V4L2_FIELD_NONE;
 941
 942        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 943                 "Clipping/aligning %dx%d format %08X\n",
 944                 f->fmt.pix.width, f->fmt.pix.height, f->fmt.pix.pixelformat);
 945
 946        v4l_bound_align_image(&f->fmt.pix.width, MIN_WIDTH, dev->max_width, 1,
 947                              &f->fmt.pix.height, MIN_HEIGHT, dev->max_height,
 948                              1, 0);
 949        f->fmt.pix.bytesperline = f->fmt.pix.width * mfmt->ybbp;
 950        if (!mfmt->remove_padding) {
 951                if (mfmt->depth == 24) {
 952                        /*
 953                         * 24bpp is a pain as we can't use simple masking.
 954                         * Min stride is width aligned to 16, times 24bpp.
 955                         */
 956                        f->fmt.pix.bytesperline =
 957                                ((f->fmt.pix.width + 15) & ~15) * 3;
 958                } else {
 959                        /*
 960                         * GPU isn't removing padding, so stride is aligned to
 961                         * 32
 962                         */
 963                        int align_mask = ((32 * mfmt->depth) >> 3) - 1;
 964
 965                        f->fmt.pix.bytesperline =
 966                                (f->fmt.pix.bytesperline + align_mask) &
 967                                                        ~align_mask;
 968                }
 969                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 970                         "Not removing padding, so bytes/line = %d\n",
 971                         f->fmt.pix.bytesperline);
 972        }
 973
 974        /* Image buffer has to be padded to allow for alignment, even though
 975         * we sometimes then remove that padding before delivering the buffer.
 976         */
 977        f->fmt.pix.sizeimage = ((f->fmt.pix.height + 15) & ~15) *
 978                        (((f->fmt.pix.width + 31) & ~31) * mfmt->depth) >> 3;
 979
 980        if ((mfmt->flags & V4L2_FMT_FLAG_COMPRESSED) &&
 981            f->fmt.pix.sizeimage < MIN_BUFFER_SIZE)
 982                f->fmt.pix.sizeimage = MIN_BUFFER_SIZE;
 983
 984        if (f->fmt.pix.pixelformat == V4L2_PIX_FMT_RGB24)
 985                f->fmt.pix.colorspace = V4L2_COLORSPACE_SRGB;
 986        else if (f->fmt.pix.pixelformat == V4L2_PIX_FMT_JPEG)
 987                f->fmt.pix.colorspace = V4L2_COLORSPACE_JPEG;
 988        else
 989                f->fmt.pix.colorspace = V4L2_COLORSPACE_SMPTE170M;
 990        f->fmt.pix.priv = 0;
 991
 992        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
 993                 "Now %dx%d format %08X\n",
 994                f->fmt.pix.width, f->fmt.pix.height, f->fmt.pix.pixelformat);
 995
 996        v4l2_dump_pix_format(1, bcm2835_v4l2_debug, &dev->v4l2_dev, &f->fmt.pix,
 997                             __func__);
 998        return 0;
 999}
1000
1001static int mmal_setup_components(struct bm2835_mmal_dev *dev,
1002                                 struct v4l2_format *f)
1003{
1004        int ret;
1005        struct vchiq_mmal_port *port = NULL, *camera_port = NULL;
1006        struct vchiq_mmal_component *encode_component = NULL;
1007        struct mmal_fmt *mfmt = get_format(f);
1008        u32 remove_padding;
1009
1010        if (!mfmt)
1011                return -EINVAL;
1012
1013        if (dev->capture.encode_component) {
1014                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
1015                         "vid_cap - disconnect previous tunnel\n");
1016
1017                /* Disconnect any previous connection */
1018                vchiq_mmal_port_connect_tunnel(dev->instance,
1019                                               dev->capture.camera_port, NULL);
1020                dev->capture.camera_port = NULL;
1021                ret = vchiq_mmal_component_disable(dev->instance,
1022                                                   dev->capture.encode_component);
1023                if (ret)
1024                        v4l2_err(&dev->v4l2_dev,
1025                                 "Failed to disable encode component %d\n",
1026                                 ret);
1027
1028                dev->capture.encode_component = NULL;
1029        }
1030        /* format dependent port setup */
1031        switch (mfmt->mmal_component) {
1032        case COMP_CAMERA:
1033                /* Make a further decision on port based on resolution */
1034                if (f->fmt.pix.width <= max_video_width &&
1035                    f->fmt.pix.height <= max_video_height)
1036                        camera_port =
1037                            &dev->component[COMP_CAMERA]->output[CAM_PORT_VIDEO];
1038                else
1039                        camera_port =
1040                            &dev->component[COMP_CAMERA]->output[CAM_PORT_CAPTURE];
1041                port = camera_port;
1042                break;
1043        case COMP_IMAGE_ENCODE:
1044                encode_component = dev->component[COMP_IMAGE_ENCODE];
1045                port = &dev->component[COMP_IMAGE_ENCODE]->output[0];
1046                camera_port =
1047                    &dev->component[COMP_CAMERA]->output[CAM_PORT_CAPTURE];
1048                break;
1049        case COMP_VIDEO_ENCODE:
1050                encode_component = dev->component[COMP_VIDEO_ENCODE];
1051                port = &dev->component[COMP_VIDEO_ENCODE]->output[0];
1052                camera_port =
1053                    &dev->component[COMP_CAMERA]->output[CAM_PORT_VIDEO];
1054                break;
1055        default:
1056                break;
1057        }
1058
1059        if (!port)
1060                return -EINVAL;
1061
1062        if (encode_component)
1063                camera_port->format.encoding = MMAL_ENCODING_OPAQUE;
1064        else
1065                camera_port->format.encoding = mfmt->mmal;
1066
1067        if (dev->rgb_bgr_swapped) {
1068                if (camera_port->format.encoding == MMAL_ENCODING_RGB24)
1069                        camera_port->format.encoding = MMAL_ENCODING_BGR24;
1070                else if (camera_port->format.encoding == MMAL_ENCODING_BGR24)
1071                        camera_port->format.encoding = MMAL_ENCODING_RGB24;
1072        }
1073
1074        remove_padding = mfmt->remove_padding;
1075        vchiq_mmal_port_parameter_set(dev->instance,
1076                                      camera_port,
1077                                      MMAL_PARAMETER_NO_IMAGE_PADDING,
1078                                      &remove_padding, sizeof(remove_padding));
1079
1080        camera_port->format.encoding_variant = 0;
1081        camera_port->es.video.width = f->fmt.pix.width;
1082        camera_port->es.video.height = f->fmt.pix.height;
1083        camera_port->es.video.crop.x = 0;
1084        camera_port->es.video.crop.y = 0;
1085        camera_port->es.video.crop.width = f->fmt.pix.width;
1086        camera_port->es.video.crop.height = f->fmt.pix.height;
1087        camera_port->es.video.frame_rate.num = 0;
1088        camera_port->es.video.frame_rate.den = 1;
1089        camera_port->es.video.color_space = MMAL_COLOR_SPACE_JPEG_JFIF;
1090
1091        ret = vchiq_mmal_port_set_format(dev->instance, camera_port);
1092
1093        if (!ret
1094            && camera_port ==
1095            &dev->component[COMP_CAMERA]->output[CAM_PORT_VIDEO]) {
1096                bool overlay_enabled =
1097                    !!dev->component[COMP_PREVIEW]->enabled;
1098                struct vchiq_mmal_port *preview_port =
1099                    &dev->component[COMP_CAMERA]->output[CAM_PORT_PREVIEW];
1100                /* Preview and encode ports need to match on resolution */
1101                if (overlay_enabled) {
1102                        /* Need to disable the overlay before we can update
1103                         * the resolution
1104                         */
1105                        ret =
1106                            vchiq_mmal_port_disable(dev->instance,
1107                                                    preview_port);
1108                        if (!ret)
1109                                ret =
1110                                    vchiq_mmal_port_connect_tunnel(
1111                                                dev->instance,
1112                                                preview_port,
1113                                                NULL);
1114                }
1115                preview_port->es.video.width = f->fmt.pix.width;
1116                preview_port->es.video.height = f->fmt.pix.height;
1117                preview_port->es.video.crop.x = 0;
1118                preview_port->es.video.crop.y = 0;
1119                preview_port->es.video.crop.width = f->fmt.pix.width;
1120                preview_port->es.video.crop.height = f->fmt.pix.height;
1121                preview_port->es.video.frame_rate.num =
1122                                          dev->capture.timeperframe.denominator;
1123                preview_port->es.video.frame_rate.den =
1124                                          dev->capture.timeperframe.numerator;
1125                ret = vchiq_mmal_port_set_format(dev->instance, preview_port);
1126                if (overlay_enabled) {
1127                        ret = vchiq_mmal_port_connect_tunnel(
1128                                dev->instance,
1129                                preview_port,
1130                                &dev->component[COMP_PREVIEW]->input[0]);
1131                        if (!ret)
1132                                ret = vchiq_mmal_port_enable(dev->instance,
1133                                                             preview_port,
1134                                                             NULL);
1135                }
1136        }
1137
1138        if (ret) {
1139                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
1140                         "%s failed to set format %dx%d %08X\n", __func__,
1141                         f->fmt.pix.width, f->fmt.pix.height,
1142                         f->fmt.pix.pixelformat);
1143                /* ensure capture is not going to be tried */
1144                dev->capture.port = NULL;
1145        } else {
1146                if (encode_component) {
1147                        v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
1148                                 "vid_cap - set up encode comp\n");
1149
1150                        /* configure buffering */
1151                        camera_port->current_buffer.size =
1152                            camera_port->recommended_buffer.size;
1153                        camera_port->current_buffer.num =
1154                            camera_port->recommended_buffer.num;
1155
1156                        ret =
1157                            vchiq_mmal_port_connect_tunnel(
1158                                        dev->instance,
1159                                        camera_port,
1160                                        &encode_component->input[0]);
1161                        if (ret) {
1162                                v4l2_dbg(1, bcm2835_v4l2_debug,
1163                                         &dev->v4l2_dev,
1164                                         "%s failed to create connection\n",
1165                                         __func__);
1166                                /* ensure capture is not going to be tried */
1167                                dev->capture.port = NULL;
1168                        } else {
1169                                port->es.video.width = f->fmt.pix.width;
1170                                port->es.video.height = f->fmt.pix.height;
1171                                port->es.video.crop.x = 0;
1172                                port->es.video.crop.y = 0;
1173                                port->es.video.crop.width = f->fmt.pix.width;
1174                                port->es.video.crop.height = f->fmt.pix.height;
1175                                port->es.video.frame_rate.num =
1176                                          dev->capture.timeperframe.denominator;
1177                                port->es.video.frame_rate.den =
1178                                          dev->capture.timeperframe.numerator;
1179
1180                                port->format.encoding = mfmt->mmal;
1181                                port->format.encoding_variant = 0;
1182                                /* Set any encoding specific parameters */
1183                                switch (mfmt->mmal_component) {
1184                                case COMP_VIDEO_ENCODE:
1185                                        port->format.bitrate =
1186                                            dev->capture.encode_bitrate;
1187                                        break;
1188                                case COMP_IMAGE_ENCODE:
1189                                        /* Could set EXIF parameters here */
1190                                        break;
1191                                default:
1192                                        break;
1193                                }
1194                                ret = vchiq_mmal_port_set_format(dev->instance,
1195                                                                 port);
1196                                if (ret)
1197                                        v4l2_dbg(1, bcm2835_v4l2_debug,
1198                                                 &dev->v4l2_dev,
1199                                                 "%s failed to set format %dx%d fmt %08X\n",
1200                                                 __func__,
1201                                                 f->fmt.pix.width,
1202                                                 f->fmt.pix.height,
1203                                                 f->fmt.pix.pixelformat
1204                                                 );
1205                        }
1206
1207                        if (!ret) {
1208                                ret = vchiq_mmal_component_enable(
1209                                                dev->instance,
1210                                                encode_component);
1211                                if (ret) {
1212                                        v4l2_dbg(1, bcm2835_v4l2_debug,
1213                                                 &dev->v4l2_dev,
1214                                                 "%s Failed to enable encode components\n",
1215                                                 __func__);
1216                                }
1217                        }
1218                        if (!ret) {
1219                                /* configure buffering */
1220                                port->current_buffer.num = 1;
1221                                port->current_buffer.size =
1222                                    f->fmt.pix.sizeimage;
1223                                if (port->format.encoding ==
1224                                    MMAL_ENCODING_JPEG) {
1225                                        v4l2_dbg(1, bcm2835_v4l2_debug,
1226                                                 &dev->v4l2_dev,
1227                                                 "JPG - buf size now %d was %d\n",
1228                                                 f->fmt.pix.sizeimage,
1229                                                 port->current_buffer.size);
1230                                        port->current_buffer.size =
1231                                            (f->fmt.pix.sizeimage <
1232                                             (100 << 10)) ?
1233                                            (100 << 10) : f->fmt.pix.sizeimage;
1234                                }
1235                                v4l2_dbg(1, bcm2835_v4l2_debug,
1236                                         &dev->v4l2_dev,
1237                                         "vid_cap - cur_buf.size set to %d\n",
1238                                         f->fmt.pix.sizeimage);
1239                                port->current_buffer.alignment = 0;
1240                        }
1241                } else {
1242                        /* configure buffering */
1243                        camera_port->current_buffer.num = 1;
1244                        camera_port->current_buffer.size = f->fmt.pix.sizeimage;
1245                        camera_port->current_buffer.alignment = 0;
1246                }
1247
1248                if (!ret) {
1249                        dev->capture.fmt = mfmt;
1250                        dev->capture.stride = f->fmt.pix.bytesperline;
1251                        dev->capture.width = camera_port->es.video.crop.width;
1252                        dev->capture.height = camera_port->es.video.crop.height;
1253                        dev->capture.buffersize = port->current_buffer.size;
1254
1255                        /* select port for capture */
1256                        dev->capture.port = port;
1257                        dev->capture.camera_port = camera_port;
1258                        dev->capture.encode_component = encode_component;
1259                        v4l2_dbg(1, bcm2835_v4l2_debug,
1260                                 &dev->v4l2_dev,
1261                                "Set dev->capture.fmt %08X, %dx%d, stride %d, size %d",
1262                                port->format.encoding,
1263                                dev->capture.width, dev->capture.height,
1264                                dev->capture.stride, dev->capture.buffersize);
1265                }
1266        }
1267
1268        /* todo: Need to convert the vchiq/mmal error into a v4l2 error. */
1269        return ret;
1270}
1271
1272static int vidioc_s_fmt_vid_cap(struct file *file, void *priv,
1273                                struct v4l2_format *f)
1274{
1275        int ret;
1276        struct bm2835_mmal_dev *dev = video_drvdata(file);
1277        struct mmal_fmt *mfmt;
1278
1279        /* try the format to set valid parameters */
1280        ret = vidioc_try_fmt_vid_cap(file, priv, f);
1281        if (ret) {
1282                v4l2_err(&dev->v4l2_dev,
1283                         "vid_cap - vidioc_try_fmt_vid_cap failed\n");
1284                return ret;
1285        }
1286
1287        /* if a capture is running refuse to set format */
1288        if (vb2_is_busy(&dev->capture.vb_vidq)) {
1289                v4l2_info(&dev->v4l2_dev, "%s device busy\n", __func__);
1290                return -EBUSY;
1291        }
1292
1293        /* If the format is unsupported v4l2 says we should switch to
1294         * a supported one and not return an error.
1295         */
1296        mfmt = get_format(f);
1297        if (!mfmt) {
1298                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
1299                         "Fourcc format (0x%08x) unknown.\n",
1300                         f->fmt.pix.pixelformat);
1301                f->fmt.pix.pixelformat = formats[0].fourcc;
1302                mfmt = get_format(f);
1303        }
1304
1305        ret = mmal_setup_components(dev, f);
1306        if (ret) {
1307                v4l2_err(&dev->v4l2_dev,
1308                         "%s: failed to setup mmal components: %d\n",
1309                         __func__, ret);
1310                ret = -EINVAL;
1311        }
1312
1313        return ret;
1314}
1315
1316static int vidioc_enum_framesizes(struct file *file, void *fh,
1317                                  struct v4l2_frmsizeenum *fsize)
1318{
1319        struct bm2835_mmal_dev *dev = video_drvdata(file);
1320        static const struct v4l2_frmsize_stepwise sizes = {
1321                MIN_WIDTH, 0, 2,
1322                MIN_HEIGHT, 0, 2
1323        };
1324        int i;
1325
1326        if (fsize->index)
1327                return -EINVAL;
1328        for (i = 0; i < ARRAY_SIZE(formats); i++)
1329                if (formats[i].fourcc == fsize->pixel_format)
1330                        break;
1331        if (i == ARRAY_SIZE(formats))
1332                return -EINVAL;
1333        fsize->type = V4L2_FRMSIZE_TYPE_STEPWISE;
1334        fsize->stepwise = sizes;
1335        fsize->stepwise.max_width = dev->max_width;
1336        fsize->stepwise.max_height = dev->max_height;
1337        return 0;
1338}
1339
1340/* timeperframe is arbitrary and continuous */
1341static int vidioc_enum_frameintervals(struct file *file, void *priv,
1342                                      struct v4l2_frmivalenum *fival)
1343{
1344        struct bm2835_mmal_dev *dev = video_drvdata(file);
1345        int i;
1346
1347        if (fival->index)
1348                return -EINVAL;
1349
1350        for (i = 0; i < ARRAY_SIZE(formats); i++)
1351                if (formats[i].fourcc == fival->pixel_format)
1352                        break;
1353        if (i == ARRAY_SIZE(formats))
1354                return -EINVAL;
1355
1356        /* regarding width & height - we support any within range */
1357        if (fival->width < MIN_WIDTH || fival->width > dev->max_width ||
1358            fival->height < MIN_HEIGHT || fival->height > dev->max_height)
1359                return -EINVAL;
1360
1361        fival->type = V4L2_FRMIVAL_TYPE_CONTINUOUS;
1362
1363        /* fill in stepwise (step=1.0 is required by V4L2 spec) */
1364        fival->stepwise.min  = tpf_min;
1365        fival->stepwise.max  = tpf_max;
1366        fival->stepwise.step = (struct v4l2_fract) {1, 1};
1367
1368        return 0;
1369}
1370
1371static int vidioc_g_parm(struct file *file, void *priv,
1372                         struct v4l2_streamparm *parm)
1373{
1374        struct bm2835_mmal_dev *dev = video_drvdata(file);
1375
1376        if (parm->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1377                return -EINVAL;
1378
1379        parm->parm.capture.capability   = V4L2_CAP_TIMEPERFRAME;
1380        parm->parm.capture.timeperframe = dev->capture.timeperframe;
1381        parm->parm.capture.readbuffers  = 1;
1382        return 0;
1383}
1384
1385static int vidioc_s_parm(struct file *file, void *priv,
1386                         struct v4l2_streamparm *parm)
1387{
1388        struct bm2835_mmal_dev *dev = video_drvdata(file);
1389        struct v4l2_fract tpf;
1390
1391        if (parm->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1392                return -EINVAL;
1393
1394        tpf = parm->parm.capture.timeperframe;
1395
1396        /* tpf: {*, 0} resets timing; clip to [min, max]*/
1397        tpf = tpf.denominator ? tpf : tpf_default;
1398        tpf = V4L2_FRACT_COMPARE(tpf, <, tpf_min) ? tpf_min : tpf;
1399        tpf = V4L2_FRACT_COMPARE(tpf, >, tpf_max) ? tpf_max : tpf;
1400
1401        dev->capture.timeperframe = tpf;
1402        parm->parm.capture.timeperframe = tpf;
1403        parm->parm.capture.readbuffers  = 1;
1404        parm->parm.capture.capability   = V4L2_CAP_TIMEPERFRAME;
1405
1406        set_framerate_params(dev);
1407
1408        return 0;
1409}
1410
1411static const struct v4l2_ioctl_ops camera0_ioctl_ops = {
1412        /* overlay */
1413        .vidioc_enum_fmt_vid_overlay = vidioc_enum_fmt_vid_overlay,
1414        .vidioc_g_fmt_vid_overlay = vidioc_g_fmt_vid_overlay,
1415        .vidioc_try_fmt_vid_overlay = vidioc_try_fmt_vid_overlay,
1416        .vidioc_s_fmt_vid_overlay = vidioc_s_fmt_vid_overlay,
1417        .vidioc_overlay = vidioc_overlay,
1418        .vidioc_g_fbuf = vidioc_g_fbuf,
1419
1420        /* inputs */
1421        .vidioc_enum_input = vidioc_enum_input,
1422        .vidioc_g_input = vidioc_g_input,
1423        .vidioc_s_input = vidioc_s_input,
1424
1425        /* capture */
1426        .vidioc_querycap = vidioc_querycap,
1427        .vidioc_enum_fmt_vid_cap = vidioc_enum_fmt_vid_cap,
1428        .vidioc_g_fmt_vid_cap = vidioc_g_fmt_vid_cap,
1429        .vidioc_try_fmt_vid_cap = vidioc_try_fmt_vid_cap,
1430        .vidioc_s_fmt_vid_cap = vidioc_s_fmt_vid_cap,
1431
1432        /* buffer management */
1433        .vidioc_reqbufs = vb2_ioctl_reqbufs,
1434        .vidioc_create_bufs = vb2_ioctl_create_bufs,
1435        .vidioc_prepare_buf = vb2_ioctl_prepare_buf,
1436        .vidioc_querybuf = vb2_ioctl_querybuf,
1437        .vidioc_qbuf = vb2_ioctl_qbuf,
1438        .vidioc_dqbuf = vb2_ioctl_dqbuf,
1439        .vidioc_enum_framesizes = vidioc_enum_framesizes,
1440        .vidioc_enum_frameintervals = vidioc_enum_frameintervals,
1441        .vidioc_g_parm        = vidioc_g_parm,
1442        .vidioc_s_parm        = vidioc_s_parm,
1443        .vidioc_streamon = vb2_ioctl_streamon,
1444        .vidioc_streamoff = vb2_ioctl_streamoff,
1445
1446        .vidioc_log_status = v4l2_ctrl_log_status,
1447        .vidioc_subscribe_event = v4l2_ctrl_subscribe_event,
1448        .vidioc_unsubscribe_event = v4l2_event_unsubscribe,
1449};
1450
1451/* ------------------------------------------------------------------
1452 *      Driver init/finalise
1453 * ------------------------------------------------------------------
1454 */
1455
1456static const struct v4l2_file_operations camera0_fops = {
1457        .owner = THIS_MODULE,
1458        .open = v4l2_fh_open,
1459        .release = vb2_fop_release,
1460        .read = vb2_fop_read,
1461        .poll = vb2_fop_poll,
1462        .unlocked_ioctl = video_ioctl2, /* V4L2 ioctl handler */
1463        .mmap = vb2_fop_mmap,
1464};
1465
1466static const struct video_device vdev_template = {
1467        .name = "camera0",
1468        .fops = &camera0_fops,
1469        .ioctl_ops = &camera0_ioctl_ops,
1470        .release = video_device_release_empty,
1471        .device_caps = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_VIDEO_OVERLAY |
1472                       V4L2_CAP_STREAMING | V4L2_CAP_READWRITE,
1473};
1474
1475/* Returns the number of cameras, and also the max resolution supported
1476 * by those cameras.
1477 */
1478static int get_num_cameras(struct vchiq_mmal_instance *instance,
1479                           unsigned int resolutions[][2], int num_resolutions)
1480{
1481        int ret;
1482        struct vchiq_mmal_component  *cam_info_component;
1483        struct mmal_parameter_camera_info_t cam_info = {0};
1484        u32 param_size = sizeof(cam_info);
1485        int i;
1486
1487        /* create a camera_info component */
1488        ret = vchiq_mmal_component_init(instance, "camera_info",
1489                                        &cam_info_component);
1490        if (ret < 0)
1491                /* Unusual failure - let's guess one camera. */
1492                return 1;
1493
1494        if (vchiq_mmal_port_parameter_get(instance,
1495                                          &cam_info_component->control,
1496                                          MMAL_PARAMETER_CAMERA_INFO,
1497                                          &cam_info,
1498                                          &param_size)) {
1499                pr_info("Failed to get camera info\n");
1500        }
1501        for (i = 0;
1502             i < min_t(unsigned int, cam_info.num_cameras, num_resolutions);
1503             i++) {
1504                resolutions[i][0] = cam_info.cameras[i].max_width;
1505                resolutions[i][1] = cam_info.cameras[i].max_height;
1506        }
1507
1508        vchiq_mmal_component_finalise(instance,
1509                                      cam_info_component);
1510
1511        return cam_info.num_cameras;
1512}
1513
1514static int set_camera_parameters(struct vchiq_mmal_instance *instance,
1515                                 struct vchiq_mmal_component *camera,
1516                                 struct bm2835_mmal_dev *dev)
1517{
1518        struct mmal_parameter_camera_config cam_config = {
1519                .max_stills_w = dev->max_width,
1520                .max_stills_h = dev->max_height,
1521                .stills_yuv422 = 1,
1522                .one_shot_stills = 1,
1523                .max_preview_video_w = (max_video_width > 1920) ?
1524                                                max_video_width : 1920,
1525                .max_preview_video_h = (max_video_height > 1088) ?
1526                                                max_video_height : 1088,
1527                .num_preview_video_frames = 3,
1528                .stills_capture_circular_buffer_height = 0,
1529                .fast_preview_resume = 0,
1530                .use_stc_timestamp = MMAL_PARAM_TIMESTAMP_MODE_RAW_STC
1531        };
1532
1533        return vchiq_mmal_port_parameter_set(instance, &camera->control,
1534                                            MMAL_PARAMETER_CAMERA_CONFIG,
1535                                            &cam_config, sizeof(cam_config));
1536}
1537
1538#define MAX_SUPPORTED_ENCODINGS 20
1539
1540/* MMAL instance and component init */
1541static int mmal_init(struct bm2835_mmal_dev *dev)
1542{
1543        int ret;
1544        struct mmal_es_format_local *format;
1545        u32 supported_encodings[MAX_SUPPORTED_ENCODINGS];
1546        u32 param_size;
1547        struct vchiq_mmal_component  *camera;
1548
1549        ret = vchiq_mmal_init(&dev->instance);
1550        if (ret < 0) {
1551                v4l2_err(&dev->v4l2_dev, "%s: vchiq mmal init failed %d\n",
1552                         __func__, ret);
1553                return ret;
1554        }
1555
1556        /* get the camera component ready */
1557        ret = vchiq_mmal_component_init(dev->instance, "ril.camera",
1558                                        &dev->component[COMP_CAMERA]);
1559        if (ret < 0)
1560                goto unreg_mmal;
1561
1562        camera = dev->component[COMP_CAMERA];
1563        if (camera->outputs < CAM_PORT_COUNT) {
1564                v4l2_err(&dev->v4l2_dev, "%s: too few camera outputs %d needed %d\n",
1565                         __func__, camera->outputs, CAM_PORT_COUNT);
1566                ret = -EINVAL;
1567                goto unreg_camera;
1568        }
1569
1570        ret = set_camera_parameters(dev->instance,
1571                                    camera,
1572                                    dev);
1573        if (ret < 0) {
1574                v4l2_err(&dev->v4l2_dev, "%s: unable to set camera parameters: %d\n",
1575                         __func__, ret);
1576                goto unreg_camera;
1577        }
1578
1579        /* There was an error in the firmware that meant the camera component
1580         * produced BGR instead of RGB.
1581         * This is now fixed, but in order to support the old firmwares, we
1582         * have to check.
1583         */
1584        dev->rgb_bgr_swapped = true;
1585        param_size = sizeof(supported_encodings);
1586        ret = vchiq_mmal_port_parameter_get(dev->instance,
1587                                            &camera->output[CAM_PORT_CAPTURE],
1588                                            MMAL_PARAMETER_SUPPORTED_ENCODINGS,
1589                                            &supported_encodings,
1590                                            &param_size);
1591        if (ret == 0) {
1592                int i;
1593
1594                for (i = 0; i < param_size / sizeof(u32); i++) {
1595                        if (supported_encodings[i] == MMAL_ENCODING_BGR24) {
1596                                /* Found BGR24 first - old firmware. */
1597                                break;
1598                        }
1599                        if (supported_encodings[i] == MMAL_ENCODING_RGB24) {
1600                                /* Found RGB24 first
1601                                 * new firmware, so use RGB24.
1602                                 */
1603                                dev->rgb_bgr_swapped = false;
1604                        break;
1605                        }
1606                }
1607        }
1608        format = &camera->output[CAM_PORT_PREVIEW].format;
1609
1610        format->encoding = MMAL_ENCODING_OPAQUE;
1611        format->encoding_variant = MMAL_ENCODING_I420;
1612
1613        format->es->video.width = 1024;
1614        format->es->video.height = 768;
1615        format->es->video.crop.x = 0;
1616        format->es->video.crop.y = 0;
1617        format->es->video.crop.width = 1024;
1618        format->es->video.crop.height = 768;
1619        format->es->video.frame_rate.num = 0; /* Rely on fps_range */
1620        format->es->video.frame_rate.den = 1;
1621
1622        format = &camera->output[CAM_PORT_VIDEO].format;
1623
1624        format->encoding = MMAL_ENCODING_OPAQUE;
1625        format->encoding_variant = MMAL_ENCODING_I420;
1626
1627        format->es->video.width = 1024;
1628        format->es->video.height = 768;
1629        format->es->video.crop.x = 0;
1630        format->es->video.crop.y = 0;
1631        format->es->video.crop.width = 1024;
1632        format->es->video.crop.height = 768;
1633        format->es->video.frame_rate.num = 0; /* Rely on fps_range */
1634        format->es->video.frame_rate.den = 1;
1635
1636        format = &camera->output[CAM_PORT_CAPTURE].format;
1637
1638        format->encoding = MMAL_ENCODING_OPAQUE;
1639
1640        format->es->video.width = 2592;
1641        format->es->video.height = 1944;
1642        format->es->video.crop.x = 0;
1643        format->es->video.crop.y = 0;
1644        format->es->video.crop.width = 2592;
1645        format->es->video.crop.height = 1944;
1646        format->es->video.frame_rate.num = 0; /* Rely on fps_range */
1647        format->es->video.frame_rate.den = 1;
1648
1649        dev->capture.width = format->es->video.width;
1650        dev->capture.height = format->es->video.height;
1651        dev->capture.fmt = &formats[0];
1652        dev->capture.encode_component = NULL;
1653        dev->capture.timeperframe = tpf_default;
1654        dev->capture.enc_profile = V4L2_MPEG_VIDEO_H264_PROFILE_HIGH;
1655        dev->capture.enc_level = V4L2_MPEG_VIDEO_H264_LEVEL_4_0;
1656
1657        /* get the preview component ready */
1658        ret = vchiq_mmal_component_init(
1659                        dev->instance, "ril.video_render",
1660                        &dev->component[COMP_PREVIEW]);
1661        if (ret < 0)
1662                goto unreg_camera;
1663
1664        if (dev->component[COMP_PREVIEW]->inputs < 1) {
1665                ret = -EINVAL;
1666                v4l2_err(&dev->v4l2_dev, "%s: too few input ports %d needed %d\n",
1667                         __func__, dev->component[COMP_PREVIEW]->inputs, 1);
1668                goto unreg_preview;
1669        }
1670
1671        /* get the image encoder component ready */
1672        ret = vchiq_mmal_component_init(
1673                dev->instance, "ril.image_encode",
1674                &dev->component[COMP_IMAGE_ENCODE]);
1675        if (ret < 0)
1676                goto unreg_preview;
1677
1678        if (dev->component[COMP_IMAGE_ENCODE]->inputs < 1) {
1679                ret = -EINVAL;
1680                v4l2_err(&dev->v4l2_dev, "%s: too few input ports %d needed %d\n",
1681                         __func__, dev->component[COMP_IMAGE_ENCODE]->inputs,
1682                         1);
1683                goto unreg_image_encoder;
1684        }
1685
1686        /* get the video encoder component ready */
1687        ret = vchiq_mmal_component_init(dev->instance, "ril.video_encode",
1688                                        &dev->component[COMP_VIDEO_ENCODE]);
1689        if (ret < 0)
1690                goto unreg_image_encoder;
1691
1692        if (dev->component[COMP_VIDEO_ENCODE]->inputs < 1) {
1693                ret = -EINVAL;
1694                v4l2_err(&dev->v4l2_dev, "%s: too few input ports %d needed %d\n",
1695                         __func__, dev->component[COMP_VIDEO_ENCODE]->inputs,
1696                         1);
1697                goto unreg_vid_encoder;
1698        }
1699
1700        {
1701                struct vchiq_mmal_port *encoder_port =
1702                        &dev->component[COMP_VIDEO_ENCODE]->output[0];
1703                encoder_port->format.encoding = MMAL_ENCODING_H264;
1704                ret = vchiq_mmal_port_set_format(dev->instance,
1705                                                 encoder_port);
1706        }
1707
1708        {
1709                unsigned int enable = 1;
1710
1711                vchiq_mmal_port_parameter_set(
1712                        dev->instance,
1713                        &dev->component[COMP_VIDEO_ENCODE]->control,
1714                        MMAL_PARAMETER_VIDEO_IMMUTABLE_INPUT,
1715                        &enable, sizeof(enable));
1716
1717                vchiq_mmal_port_parameter_set(dev->instance,
1718                                              &dev->component[COMP_VIDEO_ENCODE]->control,
1719                                              MMAL_PARAMETER_MINIMISE_FRAGMENTATION,
1720                                              &enable,
1721                                              sizeof(enable));
1722        }
1723        ret = bm2835_mmal_set_all_camera_controls(dev);
1724        if (ret < 0) {
1725                v4l2_err(&dev->v4l2_dev, "%s: failed to set all camera controls: %d\n",
1726                         __func__, ret);
1727                goto unreg_vid_encoder;
1728        }
1729
1730        return 0;
1731
1732unreg_vid_encoder:
1733        pr_err("Cleanup: Destroy video encoder\n");
1734        vchiq_mmal_component_finalise(
1735                dev->instance,
1736                dev->component[COMP_VIDEO_ENCODE]);
1737
1738unreg_image_encoder:
1739        pr_err("Cleanup: Destroy image encoder\n");
1740        vchiq_mmal_component_finalise(
1741                dev->instance,
1742                dev->component[COMP_IMAGE_ENCODE]);
1743
1744unreg_preview:
1745        pr_err("Cleanup: Destroy video render\n");
1746        vchiq_mmal_component_finalise(dev->instance,
1747                                      dev->component[COMP_PREVIEW]);
1748
1749unreg_camera:
1750        pr_err("Cleanup: Destroy camera\n");
1751        vchiq_mmal_component_finalise(dev->instance,
1752                                      dev->component[COMP_CAMERA]);
1753
1754unreg_mmal:
1755        vchiq_mmal_finalise(dev->instance);
1756        return ret;
1757}
1758
1759static int bm2835_mmal_init_device(struct bm2835_mmal_dev *dev,
1760                                   struct video_device *vfd)
1761{
1762        int ret;
1763
1764        *vfd = vdev_template;
1765
1766        vfd->v4l2_dev = &dev->v4l2_dev;
1767
1768        vfd->lock = &dev->mutex;
1769
1770        vfd->queue = &dev->capture.vb_vidq;
1771
1772        /* video device needs to be able to access instance data */
1773        video_set_drvdata(vfd, dev);
1774
1775        ret = video_register_device(vfd,
1776                                    VFL_TYPE_GRABBER,
1777                                    video_nr[dev->camera_num]);
1778        if (ret < 0)
1779                return ret;
1780
1781        v4l2_info(vfd->v4l2_dev,
1782                  "V4L2 device registered as %s - stills mode > %dx%d\n",
1783                  video_device_node_name(vfd),
1784                  max_video_width, max_video_height);
1785
1786        return 0;
1787}
1788
1789static void bcm2835_cleanup_instance(struct bm2835_mmal_dev *dev)
1790{
1791        if (!dev)
1792                return;
1793
1794        v4l2_info(&dev->v4l2_dev, "unregistering %s\n",
1795                  video_device_node_name(&dev->vdev));
1796
1797        video_unregister_device(&dev->vdev);
1798
1799        if (dev->capture.encode_component) {
1800                v4l2_dbg(1, bcm2835_v4l2_debug, &dev->v4l2_dev,
1801                         "mmal_exit - disconnect tunnel\n");
1802                vchiq_mmal_port_connect_tunnel(dev->instance,
1803                                               dev->capture.camera_port, NULL);
1804                vchiq_mmal_component_disable(dev->instance,
1805                                             dev->capture.encode_component);
1806        }
1807        vchiq_mmal_component_disable(dev->instance,
1808                                     dev->component[COMP_CAMERA]);
1809
1810        vchiq_mmal_component_finalise(dev->instance,
1811                                      dev->component[COMP_VIDEO_ENCODE]);
1812
1813        vchiq_mmal_component_finalise(dev->instance,
1814                                      dev->component[COMP_IMAGE_ENCODE]);
1815
1816        vchiq_mmal_component_finalise(dev->instance,
1817                                      dev->component[COMP_PREVIEW]);
1818
1819        vchiq_mmal_component_finalise(dev->instance,
1820                                      dev->component[COMP_CAMERA]);
1821
1822        v4l2_ctrl_handler_free(&dev->ctrl_handler);
1823
1824        v4l2_device_unregister(&dev->v4l2_dev);
1825
1826        kfree(dev);
1827}
1828
1829static struct v4l2_format default_v4l2_format = {
1830        .fmt.pix.pixelformat = V4L2_PIX_FMT_JPEG,
1831        .fmt.pix.width = 1024,
1832        .fmt.pix.bytesperline = 0,
1833        .fmt.pix.height = 768,
1834        .fmt.pix.sizeimage = 1024 * 768,
1835};
1836
1837static int bcm2835_mmal_probe(struct platform_device *pdev)
1838{
1839        int ret;
1840        struct bm2835_mmal_dev *dev;
1841        struct vb2_queue *q;
1842        int camera;
1843        unsigned int num_cameras;
1844        struct vchiq_mmal_instance *instance;
1845        unsigned int resolutions[MAX_BCM2835_CAMERAS][2];
1846        int i;
1847
1848        ret = vchiq_mmal_init(&instance);
1849        if (ret < 0)
1850                return ret;
1851
1852        num_cameras = get_num_cameras(instance,
1853                                      resolutions,
1854                                      MAX_BCM2835_CAMERAS);
1855
1856        if (num_cameras < 1) {
1857                ret = -ENODEV;
1858                goto cleanup_mmal;
1859        }
1860
1861        if (num_cameras > MAX_BCM2835_CAMERAS)
1862                num_cameras = MAX_BCM2835_CAMERAS;
1863
1864        for (camera = 0; camera < num_cameras; camera++) {
1865                dev = kzalloc(sizeof(*dev), GFP_KERNEL);
1866                if (!dev) {
1867                        ret = -ENOMEM;
1868                        goto cleanup_gdev;
1869                }
1870
1871                /* v4l2 core mutex used to protect all fops and v4l2 ioctls. */
1872                mutex_init(&dev->mutex);
1873                dev->camera_num = camera;
1874                dev->max_width = resolutions[camera][0];
1875                dev->max_height = resolutions[camera][1];
1876
1877                /* setup device defaults */
1878                dev->overlay.w.left = 150;
1879                dev->overlay.w.top = 50;
1880                dev->overlay.w.width = 1024;
1881                dev->overlay.w.height = 768;
1882                dev->overlay.clipcount = 0;
1883                dev->overlay.field = V4L2_FIELD_NONE;
1884                dev->overlay.global_alpha = 255;
1885
1886                dev->capture.fmt = &formats[3]; /* JPEG */
1887
1888                /* v4l device registration */
1889                snprintf(dev->v4l2_dev.name, sizeof(dev->v4l2_dev.name),
1890                         "%s", BM2835_MMAL_MODULE_NAME);
1891                ret = v4l2_device_register(NULL, &dev->v4l2_dev);
1892                if (ret) {
1893                        dev_err(&pdev->dev, "%s: could not register V4L2 device: %d\n",
1894                                __func__, ret);
1895                        goto free_dev;
1896                }
1897
1898                /* setup v4l controls */
1899                ret = bm2835_mmal_init_controls(dev, &dev->ctrl_handler);
1900                if (ret < 0) {
1901                        v4l2_err(&dev->v4l2_dev, "%s: could not init controls: %d\n",
1902                                 __func__, ret);
1903                        goto unreg_dev;
1904                }
1905                dev->v4l2_dev.ctrl_handler = &dev->ctrl_handler;
1906
1907                /* mmal init */
1908                dev->instance = instance;
1909                ret = mmal_init(dev);
1910                if (ret < 0) {
1911                        v4l2_err(&dev->v4l2_dev, "%s: mmal init failed: %d\n",
1912                                 __func__, ret);
1913                        goto unreg_dev;
1914                }
1915                /* initialize queue */
1916                q = &dev->capture.vb_vidq;
1917                memset(q, 0, sizeof(*q));
1918                q->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
1919                q->io_modes = VB2_MMAP | VB2_USERPTR | VB2_READ;
1920                q->drv_priv = dev;
1921                q->buf_struct_size = sizeof(struct mmal_buffer);
1922                q->ops = &bm2835_mmal_video_qops;
1923                q->mem_ops = &vb2_vmalloc_memops;
1924                q->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC;
1925                q->lock = &dev->mutex;
1926                ret = vb2_queue_init(q);
1927                if (ret < 0)
1928                        goto unreg_dev;
1929
1930                /* initialise video devices */
1931                ret = bm2835_mmal_init_device(dev, &dev->vdev);
1932                if (ret < 0) {
1933                        v4l2_err(&dev->v4l2_dev, "%s: could not init device: %d\n",
1934                                 __func__, ret);
1935                        goto unreg_dev;
1936                }
1937
1938                /* Really want to call vidioc_s_fmt_vid_cap with the default
1939                 * format, but currently the APIs don't join up.
1940                 */
1941                ret = mmal_setup_components(dev, &default_v4l2_format);
1942                if (ret < 0) {
1943                        v4l2_err(&dev->v4l2_dev, "%s: could not setup components: %d\n",
1944                                 __func__, ret);
1945                        goto unreg_dev;
1946                }
1947
1948                v4l2_info(&dev->v4l2_dev,
1949                          "Broadcom 2835 MMAL video capture ver %s loaded.\n",
1950                          BM2835_MMAL_VERSION);
1951
1952                gdev[camera] = dev;
1953        }
1954        return 0;
1955
1956unreg_dev:
1957        v4l2_ctrl_handler_free(&dev->ctrl_handler);
1958        v4l2_device_unregister(&dev->v4l2_dev);
1959
1960free_dev:
1961        kfree(dev);
1962
1963cleanup_gdev:
1964        for (i = 0; i < camera; i++) {
1965                bcm2835_cleanup_instance(gdev[i]);
1966                gdev[i] = NULL;
1967        }
1968
1969cleanup_mmal:
1970        vchiq_mmal_finalise(instance);
1971
1972        return ret;
1973}
1974
1975static int bcm2835_mmal_remove(struct platform_device *pdev)
1976{
1977        int camera;
1978        struct vchiq_mmal_instance *instance = gdev[0]->instance;
1979
1980        for (camera = 0; camera < MAX_BCM2835_CAMERAS; camera++) {
1981                bcm2835_cleanup_instance(gdev[camera]);
1982                gdev[camera] = NULL;
1983        }
1984        vchiq_mmal_finalise(instance);
1985
1986        return 0;
1987}
1988
1989static struct platform_driver bcm2835_camera_driver = {
1990        .probe          = bcm2835_mmal_probe,
1991        .remove         = bcm2835_mmal_remove,
1992        .driver         = {
1993                .name   = "bcm2835-camera",
1994        },
1995};
1996
1997module_platform_driver(bcm2835_camera_driver)
1998
1999MODULE_DESCRIPTION("Broadcom 2835 MMAL video capture");
2000MODULE_AUTHOR("Vincent Sanders");
2001MODULE_LICENSE("GPL");
2002MODULE_VERSION(BM2835_MMAL_VERSION);
2003MODULE_ALIAS("platform:bcm2835-camera");
2004