From patchwork Fri Jun 2 21:34:30 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kevin Hilman X-Patchwork-Id: 41624 X-Patchwork-Delegate: hverkuil@xs4all.nl Received: from mail.tu-berlin.de ([130.149.7.33]) by www.linuxtv.org with esmtp (Exim 4.84_2) (envelope-from ) id 1dGuDm-0006NC-Fn; Fri, 02 Jun 2017 21:35:02 +0000 X-tubIT-Incoming-IP: 209.132.180.67 Received: from vger.kernel.org ([209.132.180.67]) by mail.tu-berlin.de (exim-4.89/mailfrontend-6) with esmtp id 1dGuDj-0004Md-6F; Fri, 02 Jun 2017 23:35:02 +0200 Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751279AbdFBVe6 (ORCPT + 1 other); Fri, 2 Jun 2017 17:34:58 -0400 Received: from mail-pg0-f42.google.com ([74.125.83.42]:33199 "EHLO mail-pg0-f42.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751180AbdFBVe5 (ORCPT ); Fri, 2 Jun 2017 17:34:57 -0400 Received: by mail-pg0-f42.google.com with SMTP id u13so2873165pgb.0 for ; Fri, 02 Jun 2017 14:34:57 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=baylibre-com.20150623.gappssmtp.com; s=20150623; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=wNBZYD8neqTVnm8q92ntNo798v30MvEDNDgTL6qOiG4=; b=mMQp5ndlnssZfrmO7hvRJWtP4IHHyNngjGwyHsfKPlkk+PgKpKWGo7vDlhEsAl2Mt/ K/NdM6urvyEmRDj5MK2aRTtHsJYHsA1nHvUoEdb2zJDFV2DunWOYDK6VXnBnCcpJ8RBa 9lMINInKftr37+s2OTxktGtAazU700dq9Yoxe9DRm4T1K8u/WjHa0uVW6O1mcw7canjd 6JfG6EToMZLqWzhlrs22Jn6dEg1fSnW/mjIaF5XB3D2mW4WjgDFVvD75ZflaIPyo7qty SeFOjIk9cXj1/9MAV+zddsYnh+D1YjAVopfY2mNMtvhlP+aEY7QMhh1+vIgYbWa4MB2v is1A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=wNBZYD8neqTVnm8q92ntNo798v30MvEDNDgTL6qOiG4=; b=MvLT3SkWHKFGlM4Qdh3ZmU1vbpMGuOR7/ncz1N21cuqfOrKFas9J3EASe4AAId83JO +hayW4cmpKE5vbRES9tZ2yqjVAlaOfMHYei/zdNBbe3yOLOMwVKl0M3PyRZE65fsWwde S5K7dT6PqjbOTi0C40a+AaUlfwJi1WkULMXTAW+SXw9BU/3vVqD6Foy9Y5x7ZU7IT7W9 aDRRa6Kz5ZaolQN2aUZ0Heb9XU+0xuq/xP8TwcxgJxSUk6/KvCU5l5l0xKByMUlIE+ew LOOoDKuIEpm58NwnMvMV6HnaehKGxyhO13YZRXB6leMmlZMl5ax8smlTX/NEqiOdVGLM Mdtw== X-Gm-Message-State: AODbwcDtMRca2bFC9E/nQxbdzr67XVfj4T79SuGxlPqChntCFJ8iaPDo lCb+V8SHIsgP5o/0 X-Received: by 10.98.145.26 with SMTP id l26mr8755087pfe.36.1496439297118; Fri, 02 Jun 2017 14:34:57 -0700 (PDT) Received: from localhost (c-98-203-232-209.hsd1.wa.comcast.net. [98.203.232.209]) by smtp.gmail.com with ESMTPSA id 3sm44178570pfp.11.2017.06.02.14.34.55 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Fri, 02 Jun 2017 14:34:55 -0700 (PDT) From: Kevin Hilman To: Hans Verkuil , Laurent Pinchart , linux-media@vger.kernel.org Cc: Sekhar Nori , Patrick Titiano , linux-arm-kernel@lists.infradead.org Subject: [PATCH 3/4] [media] davinci: vpif_capture: cleanup raw camera support Date: Fri, 2 Jun 2017 14:34:30 -0700 Message-Id: <20170602213431.10777-4-khilman@baylibre.com> X-Mailer: git-send-email 2.9.3 In-Reply-To: <20170602213431.10777-1-khilman@baylibre.com> References: <20170602213431.10777-1-khilman@baylibre.com> MIME-Version: 1.0 Sender: linux-media-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-media@vger.kernel.org X-PMX-Version: 6.0.0.2142326, Antispam-Engine: 2.7.2.2107409, Antispam-Data: 2017.6.2.212415 X-PMX-Spam: Gauge=IIIIIIII, Probability=8%, Report=' MULTIPLE_RCPTS 0.1, HTML_00_01 0.05, HTML_00_10 0.05, BODY_SIZE_6000_6999 0, BODY_SIZE_7000_LESS 0, DATE_TZ_NA 0, DKIM_SIGNATURE 0, IN_REP_TO 0, LEGITIMATE_SIGNS 0, MSG_THREAD 0, MULTIPLE_REAL_RCPTS 0, NO_URI_HTTPS 0, REFERENCES 0, __ANY_URI 0, __CC_NAME 0, __CC_NAME_DIFF_FROM_ACC 0, __CC_REAL_NAMES 0, __CP_MEDIA_BODY 0, __CTE 0, __FROM_DOMAIN_IN_ANY_CC2 0, __FROM_DOMAIN_IN_RCPT 0, __HAS_CC_HDR 0, __HAS_FROM 0, __HAS_LIST_ID 0, __HAS_MSGID 0, __HAS_X_MAILER 0, __HAS_X_MAILING_LIST 0, __IN_REP_TO 0, __MIME_TEXT_ONLY 0, __MIME_TEXT_P 0, __MIME_TEXT_P1 0, __MIME_VERSION 0, __MULTIPLE_RCPTS_CC_X2 0, __NO_HTML_TAG_RAW 0, __REFERENCES 0, __SANE_MSGID 0, __STOCK_PHRASE_7 0, __SUBJ_ALPHA_END 0, __TO_MALFORMED_2 0, __TO_NAME 0, __TO_NAME_DIFF_FROM_ACC 0, __TO_REAL_NAMES 0, __URI_NO_WWW 0, __URI_NS , __YOUTUBE_RCVD 0' The current driver has a handful of hard-coded assumptions based on its primary use for capture of video signals. Cleanup those assumptions, and also query the subdev for format information and use that if available. Tested with 10-bit raw bayer input (SGRBG10) using the aptina,mt9v032 sensor, and also tested that composite video input still works from ti,tvp514x decoder. Both tests done on the da850-evm board with the add-on UI board. NOTE: Will need further testing for other sensors with different bus formats. Signed-off-by: Kevin Hilman --- drivers/media/platform/davinci/vpif_capture.c | 82 ++++++++++++++++++++++++++- 1 file changed, 80 insertions(+), 2 deletions(-) diff --git a/drivers/media/platform/davinci/vpif_capture.c b/drivers/media/platform/davinci/vpif_capture.c index b9d927d1e5a8..67624dbf1272 100644 --- a/drivers/media/platform/davinci/vpif_capture.c +++ b/drivers/media/platform/davinci/vpif_capture.c @@ -24,6 +24,9 @@ #include #include #include +#include + +#include #include "vpif.h" #include "vpif_capture.h" @@ -387,7 +390,8 @@ static irqreturn_t vpif_channel_isr(int irq, void *dev_id) common = &ch->common[i]; /* skip If streaming is not started in this channel */ /* Check the field format */ - if (1 == ch->vpifparams.std_info.frm_fmt) { + if (1 == ch->vpifparams.std_info.frm_fmt || + common->fmt.fmt.pix.field == V4L2_FIELD_NONE) { /* Progressive mode */ spin_lock(&common->irqlock); if (list_empty(&common->dma_queue)) { @@ -468,9 +472,38 @@ static int vpif_update_std_info(struct channel_obj *ch) struct vpif_channel_config_params *std_info = &vpifparams->std_info; struct video_obj *vid_ch = &ch->video; int index; + struct v4l2_pix_format *pixfmt = &common->fmt.fmt.pix; vpif_dbg(2, debug, "vpif_update_std_info\n"); + /* + * if called after try_fmt or g_fmt, there will already be a size + * so use that by default. + */ + if (pixfmt->width && pixfmt->height) { + if (pixfmt->field == V4L2_FIELD_ANY || + pixfmt->field == V4L2_FIELD_NONE) + pixfmt->field = V4L2_FIELD_NONE; + + vpifparams->iface.if_type = VPIF_IF_BT656; + if (pixfmt->pixelformat == V4L2_PIX_FMT_SGRBG10 || + pixfmt->pixelformat == V4L2_PIX_FMT_SBGGR8) + vpifparams->iface.if_type = VPIF_IF_RAW_BAYER; + + if (pixfmt->pixelformat == V4L2_PIX_FMT_SGRBG10) + vpifparams->params.data_sz = 1; /* 10 bits/pixel. */ + + /* + * For raw formats from camera sensors, we don't need + * the std_info from table lookup, so nothing else to do here. + */ + if (vpifparams->iface.if_type == VPIF_IF_RAW_BAYER) { + memset(std_info, 0, sizeof(struct vpif_channel_config_params)); + vpifparams->std_info.capture_format = 1; /* CCD/raw mode */ + return 0; + } + } + for (index = 0; index < vpif_ch_params_count; index++) { config = &vpif_ch_params[index]; if (config->hd_sd == 0) { @@ -939,6 +972,7 @@ static int vpif_try_fmt_vid_cap(struct file *file, void *priv, struct v4l2_pix_format *pixfmt = &fmt->fmt.pix; struct common_obj *common = &(ch->common[VPIF_VIDEO_INDEX]); + common->fmt = *fmt; vpif_update_std_info(ch); pixfmt->field = common->fmt.fmt.pix.field; @@ -947,8 +981,17 @@ static int vpif_try_fmt_vid_cap(struct file *file, void *priv, pixfmt->width = common->fmt.fmt.pix.width; pixfmt->height = common->fmt.fmt.pix.height; pixfmt->sizeimage = pixfmt->bytesperline * pixfmt->height * 2; + if (pixfmt->pixelformat == V4L2_PIX_FMT_SGRBG10) { + pixfmt->bytesperline = common->fmt.fmt.pix.width * 2; + pixfmt->sizeimage = pixfmt->bytesperline * pixfmt->height; + } pixfmt->priv = 0; + dev_dbg(vpif_dev, "%s: %d x %d; pitch=%d pixelformat=0x%08x, field=%d, size=%d\n", __func__, + pixfmt->width, pixfmt->height, + pixfmt->bytesperline, pixfmt->pixelformat, + pixfmt->field, pixfmt->sizeimage); + return 0; } @@ -965,13 +1008,47 @@ static int vpif_g_fmt_vid_cap(struct file *file, void *priv, struct video_device *vdev = video_devdata(file); struct channel_obj *ch = video_get_drvdata(vdev); struct common_obj *common = &ch->common[VPIF_VIDEO_INDEX]; + struct v4l2_pix_format *pix_fmt = &fmt->fmt.pix; + struct v4l2_subdev_format format = { + .which = V4L2_SUBDEV_FORMAT_ACTIVE, + }; + struct v4l2_mbus_framefmt *mbus_fmt = &format.format; + int ret; /* Check the validity of the buffer type */ if (common->fmt.type != fmt->type) return -EINVAL; - /* Fill in the information about format */ + /* By default, use currently set fmt */ *fmt = common->fmt; + + /* If subdev has get_fmt, use that to override */ + ret = v4l2_subdev_call(ch->sd, pad, get_fmt, NULL, &format); + if (!ret && mbus_fmt->code) { + v4l2_fill_pix_format(pix_fmt, mbus_fmt); + pix_fmt->bytesperline = pix_fmt->width; + if (mbus_fmt->code == MEDIA_BUS_FMT_SGRBG10_1X10) { + /* e.g. mt9v032 */ + pix_fmt->pixelformat = V4L2_PIX_FMT_SGRBG10; + pix_fmt->bytesperline = pix_fmt->width * 2; + } else if (mbus_fmt->code == MEDIA_BUS_FMT_UYVY8_2X8) { + /* e.g. tvp514x */ + pix_fmt->pixelformat = V4L2_PIX_FMT_NV16; + pix_fmt->bytesperline = pix_fmt->width * 2; + } else { + dev_warn(vpif_dev, "%s: Unhandled media-bus format 0x%x\n", + __func__, mbus_fmt->code); + } + pix_fmt->sizeimage = pix_fmt->bytesperline * pix_fmt->height; + dev_dbg(vpif_dev, "%s: %d x %d; pitch=%d, pixelformat=0x%08x, code=0x%x, field=%d, size=%d\n", __func__, + pix_fmt->width, pix_fmt->height, + pix_fmt->bytesperline, pix_fmt->pixelformat, + mbus_fmt->code, pix_fmt->field, pix_fmt->sizeimage); + + common->fmt = *fmt; + vpif_update_std_info(ch); + } + return 0; } @@ -1358,6 +1435,7 @@ static int vpif_probe_complete(void) /* set initial format */ ch->video.stdid = V4L2_STD_525_60; memset(&ch->video.dv_timings, 0, sizeof(ch->video.dv_timings)); + common->fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; vpif_update_std_info(ch); /* Initialize vb2 queue */