From patchwork Sun Aug 13 15:26:44 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Hans de Goede X-Patchwork-Id: 713453 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id D0E45C001B0 for ; Sun, 13 Aug 2023 15:27:48 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230325AbjHMP1p (ORCPT ); Sun, 13 Aug 2023 11:27:45 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:49064 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231269AbjHMP1o (ORCPT ); Sun, 13 Aug 2023 11:27:44 -0400 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.129.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 660991720 for ; Sun, 13 Aug 2023 08:26:58 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1691940417; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding; bh=njCjOgKGgSzDsDd00HdB6fBX7QUAsffjlxT9ptgJNyY=; b=TS6kf2JoCudSnWUVmFhWFdcb8nhLZ4QMKsdBmThTl5UVG4UqVis/b3MzNmFg3/AL4XvrFt 6BM89OtmGFR7ikpkqBocigZ6VMJkkFkGM4XU7ltETaNdXnA1GAK7GbX0D1dGH0WAIdTXul ft93Mxj7LcC12t6qUcI8IdAQyV3mOdg= Received: from mimecast-mx02.redhat.com (mimecast-mx02.redhat.com [66.187.233.88]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-571-Q-gFEzWYNEy8Yucy8BIVwA-1; Sun, 13 Aug 2023 11:26:55 -0400 X-MC-Unique: Q-gFEzWYNEy8Yucy8BIVwA-1 Received: from smtp.corp.redhat.com (int-mx08.intmail.prod.int.rdu2.redhat.com [10.11.54.8]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 3F4DF85CBE6; Sun, 13 Aug 2023 15:26:55 +0000 (UTC) Received: from localhost.localdomain (unknown [10.39.192.68]) by smtp.corp.redhat.com (Postfix) with ESMTP id 44D7FC15BAD; Sun, 13 Aug 2023 15:26:53 +0000 (UTC) From: Hans de Goede To: Mauro Carvalho Chehab , Sakari Ailus , Andy Shevchenko Cc: Hans de Goede , Kate Hsuan , Tsuchiya Yuto , Yury Luneff , Nable , andrey.i.trufanov@gmail.com, Fabio Aiuto , linux-media@vger.kernel.org, linux-staging@lists.linux.dev Subject: [PATCH 1/2] media: atomisp: Disable VCM for OV5693 for now Date: Sun, 13 Aug 2023 17:26:44 +0200 Message-ID: <20230813152645.45834-1-hdegoede@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.1 on 10.11.54.8 Precedence: bulk List-ID: X-Mailing-List: linux-media@vger.kernel.org ov5693 sensor modules have a VCM, but for unknown reasons the sensor fails to start streaming when instantiating a VCM i2c-client (and the runtime-pm link between VCM and sensor). Disable the VCM for now, until this is resolved. Signed-off-by: Hans de Goede --- drivers/staging/media/atomisp/pci/atomisp_csi2_bridge.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/drivers/staging/media/atomisp/pci/atomisp_csi2_bridge.c b/drivers/staging/media/atomisp/pci/atomisp_csi2_bridge.c index 03940c11505f..2483eaeeac73 100644 --- a/drivers/staging/media/atomisp/pci/atomisp_csi2_bridge.c +++ b/drivers/staging/media/atomisp/pci/atomisp_csi2_bridge.c @@ -521,7 +521,12 @@ static char *atomisp_csi2_get_vcm_type(struct acpi_device *adev) } static const struct acpi_device_id atomisp_sensor_configs[] = { - ATOMISP_SENSOR_CONFIG("INT33BE", 2, true), /* OV5693 */ + /* + * FIXME ov5693 modules have a VCM, but for unknown reasons + * the sensor fails to start streaming when instantiating + * an i2c-client for the VCM, so it is disabled for now. + */ + ATOMISP_SENSOR_CONFIG("INT33BE", 2, false), /* OV5693 */ {} }; From patchwork Sun Aug 13 15:26:45 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Hans de Goede X-Patchwork-Id: 713723 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 0F349C001DE for ; Sun, 13 Aug 2023 15:28:13 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230024AbjHMP2I (ORCPT ); Sun, 13 Aug 2023 11:28:08 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:43596 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231464AbjHMP2F (ORCPT ); Sun, 13 Aug 2023 11:28:05 -0400 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.129.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 1025F1713 for ; Sun, 13 Aug 2023 08:27:04 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1691940424; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=cxwYWGPZMg4kKvuXvzF+eFRn3wfdNE4VGN4hlvjg1ls=; b=SGeSMGANpZgEy6Ag46f4cBGCdXG5TC0XiUbebwJ0PLKwN7iXGAh7ZFkmkkME4EsPEcTeOj o8q/o3WYYSuaob2qkp5U3o3FvwlqmMOsdlJvz6qECXzyovrNsKPps97nF7q6LM0cUCjsN3 0EPCY+0xwSyzvcAh68nWhDNKcxabe5c= Received: from mimecast-mx02.redhat.com (66.187.233.73 [66.187.233.73]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-381-X1kz5LS8M3K6m3RUX0ySKg-1; Sun, 13 Aug 2023 11:26:57 -0400 X-MC-Unique: X1kz5LS8M3K6m3RUX0ySKg-1 Received: from smtp.corp.redhat.com (int-mx08.intmail.prod.int.rdu2.redhat.com [10.11.54.8]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 4E0723C025C0; Sun, 13 Aug 2023 15:26:57 +0000 (UTC) Received: from localhost.localdomain (unknown [10.39.192.68]) by smtp.corp.redhat.com (Postfix) with ESMTP id 7399EC15BAD; Sun, 13 Aug 2023 15:26:55 +0000 (UTC) From: Hans de Goede To: Mauro Carvalho Chehab , Sakari Ailus , Andy Shevchenko Cc: Hans de Goede , Kate Hsuan , Tsuchiya Yuto , Yury Luneff , Nable , andrey.i.trufanov@gmail.com, Fabio Aiuto , linux-media@vger.kernel.org, linux-staging@lists.linux.dev Subject: [PATCH 2/2] media: atomisp: Drop atomisp-ov5693 sensor driver Date: Sun, 13 Aug 2023 17:26:45 +0200 Message-ID: <20230813152645.45834-2-hdegoede@redhat.com> In-Reply-To: <20230813152645.45834-1-hdegoede@redhat.com> References: <20230813152645.45834-1-hdegoede@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.1 on 10.11.54.8 Precedence: bulk List-ID: X-Mailing-List: linux-media@vger.kernel.org After recent improvements to atomisp driver, the atomisp driver now works fine with the standard ov5693 driver. Drop the no longer necessary atomisp specific atomisp-ov5693 sensor driver. Signed-off-by: Hans de Goede --- drivers/staging/media/atomisp/i2c/Kconfig | 12 - drivers/staging/media/atomisp/i2c/Makefile | 1 - .../staging/media/atomisp/i2c/ov5693/Makefile | 2 - .../staging/media/atomisp/i2c/ov5693/ad5823.h | 63 - .../media/atomisp/i2c/ov5693/atomisp-ov5693.c | 1763 ----------------- .../staging/media/atomisp/i2c/ov5693/ov5693.h | 1331 ------------- 6 files changed, 3172 deletions(-) delete mode 100644 drivers/staging/media/atomisp/i2c/ov5693/Makefile delete mode 100644 drivers/staging/media/atomisp/i2c/ov5693/ad5823.h delete mode 100644 drivers/staging/media/atomisp/i2c/ov5693/atomisp-ov5693.c delete mode 100644 drivers/staging/media/atomisp/i2c/ov5693/ov5693.h diff --git a/drivers/staging/media/atomisp/i2c/Kconfig b/drivers/staging/media/atomisp/i2c/Kconfig index 2d4165cda2f1..f62d183b787f 100644 --- a/drivers/staging/media/atomisp/i2c/Kconfig +++ b/drivers/staging/media/atomisp/i2c/Kconfig @@ -57,18 +57,6 @@ config VIDEO_ATOMISP_GC0310 This is a Video4Linux2 sensor-level driver for the Galaxycore GC0310 0.3MP sensor. -config VIDEO_ATOMISP_OV5693 - tristate "Omnivision ov5693 sensor support" - depends on ACPI - depends on I2C && VIDEO_DEV - help - This is a Video4Linux2 sensor-level driver for the Micron - ov5693 5 Mpixel camera. - - ov5693 is video camera sensor. - - It currently only works with the atomisp driver. - # # Kconfig for flash drivers # diff --git a/drivers/staging/media/atomisp/i2c/Makefile b/drivers/staging/media/atomisp/i2c/Makefile index fc55af5f3422..e946cc91e5ff 100644 --- a/drivers/staging/media/atomisp/i2c/Makefile +++ b/drivers/staging/media/atomisp/i2c/Makefile @@ -3,7 +3,6 @@ # Makefile for sensor drivers # -obj-$(CONFIG_VIDEO_ATOMISP_OV5693) += ov5693/ obj-$(CONFIG_VIDEO_ATOMISP_MT9M114) += atomisp-mt9m114.o obj-$(CONFIG_VIDEO_ATOMISP_GC2235) += atomisp-gc2235.o obj-$(CONFIG_VIDEO_ATOMISP_OV2722) += atomisp-ov2722.o diff --git a/drivers/staging/media/atomisp/i2c/ov5693/Makefile b/drivers/staging/media/atomisp/i2c/ov5693/Makefile deleted file mode 100644 index 3275f2be229e..000000000000 --- a/drivers/staging/media/atomisp/i2c/ov5693/Makefile +++ /dev/null @@ -1,2 +0,0 @@ -# SPDX-License-Identifier: GPL-2.0 -obj-$(CONFIG_VIDEO_ATOMISP_OV5693) += atomisp-ov5693.o diff --git a/drivers/staging/media/atomisp/i2c/ov5693/ad5823.h b/drivers/staging/media/atomisp/i2c/ov5693/ad5823.h deleted file mode 100644 index f1362cd69f6e..000000000000 --- a/drivers/staging/media/atomisp/i2c/ov5693/ad5823.h +++ /dev/null @@ -1,63 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ -/* - * Support for AD5823 VCM. - * - * Copyright (c) 2013 Intel Corporation. All Rights Reserved. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License version - * 2 as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * - */ - -#ifndef __AD5823_H__ -#define __AD5823_H__ - -#include - -#define AD5823_VCM_ADDR 0x0c - -#define AD5823_REG_RESET 0x01 -#define AD5823_REG_MODE 0x02 -#define AD5823_REG_VCM_MOVE_TIME 0x03 -#define AD5823_REG_VCM_CODE_MSB 0x04 -#define AD5823_REG_VCM_CODE_LSB 0x05 -#define AD5823_REG_VCM_THRESHOLD_MSB 0x06 -#define AD5823_REG_VCM_THRESHOLD_LSB 0x07 - -#define AD5823_REG_LENGTH 0x1 - -#define AD5823_RING_CTRL_ENABLE 0x04 -#define AD5823_RING_CTRL_DISABLE 0x00 - -#define AD5823_RESONANCE_PERIOD 100000 -#define AD5823_RESONANCE_COEF 512 -#define AD5823_HIGH_FREQ_RANGE 0x80 - -#define VCM_CODE_MSB_MASK 0xfc -#define AD5823_INIT_FOCUS_POS 350 - -enum ad5823_tok_type { - AD5823_8BIT = 0x1, - AD5823_16BIT = 0x2, -}; - -enum ad5823_vcm_mode { - AD5823_ARC_RES0 = 0x0, /* Actuator response control RES1 */ - AD5823_ARC_RES1 = 0x1, /* Actuator response control RES0.5 */ - AD5823_ARC_RES2 = 0x2, /* Actuator response control RES2 */ - AD5823_ESRC = 0x3, /* Enhanced slew rate control */ - AD5823_DIRECT = 0x4, /* Direct control */ -}; - -#define AD5823_INVALID_CONFIG 0xffffffff -#define AD5823_MAX_FOCUS_POS 1023 -#define DELAY_PER_STEP_NS 1000000 -#define DELAY_MAX_PER_STEP_NS (1000000 * 1023) -#endif diff --git a/drivers/staging/media/atomisp/i2c/ov5693/atomisp-ov5693.c b/drivers/staging/media/atomisp/i2c/ov5693/atomisp-ov5693.c deleted file mode 100644 index 460a4e34c55b..000000000000 --- a/drivers/staging/media/atomisp/i2c/ov5693/atomisp-ov5693.c +++ /dev/null @@ -1,1763 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0 -/* - * Support for OmniVision OV5693 1080p HD camera sensor. - * - * Copyright (c) 2013 Intel Corporation. All Rights Reserved. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License version - * 2 as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include "../../include/linux/atomisp_gmin_platform.h" - -#include "ov5693.h" -#include "ad5823.h" - -#define __cci_delay(t) \ - do { \ - if ((t) < 10) { \ - usleep_range((t) * 1000, ((t) + 1) * 1000); \ - } else { \ - msleep((t)); \ - } \ - } while (0) - -/* Value 30ms reached through experimentation on byt ecs. - * The DS specifies a much lower value but when using a smaller value - * the I2C bus sometimes locks up permanently when starting the camera. - * This issue could not be reproduced on cht, so we can reduce the - * delay value to a lower value when insmod. - */ -static uint up_delay = 30; -module_param(up_delay, uint, 0644); -MODULE_PARM_DESC(up_delay, - "Delay prior to the first CCI transaction for ov5693"); - -static int vcm_ad_i2c_wr8(struct i2c_client *client, u8 reg, u8 val) -{ - int err; - struct i2c_msg msg; - u8 buf[2]; - - buf[0] = reg; - buf[1] = val; - - msg.addr = VCM_ADDR; - msg.flags = 0; - msg.len = 2; - msg.buf = &buf[0]; - - err = i2c_transfer(client->adapter, &msg, 1); - if (err != 1) { - dev_err(&client->dev, "%s: vcm i2c fail, err code = %d\n", - __func__, err); - return -EIO; - } - return 0; -} - -static int ad5823_i2c_write(struct i2c_client *client, u8 reg, u8 val) -{ - struct i2c_msg msg; - u8 buf[2]; - - buf[0] = reg; - buf[1] = val; - msg.addr = AD5823_VCM_ADDR; - msg.flags = 0; - msg.len = 0x02; - msg.buf = &buf[0]; - - if (i2c_transfer(client->adapter, &msg, 1) != 1) - return -EIO; - return 0; -} - -static int ad5823_i2c_read(struct i2c_client *client, u8 reg, u8 *val) -{ - struct i2c_msg msg[2]; - u8 buf[2]; - - buf[0] = reg; - buf[1] = 0; - - msg[0].addr = AD5823_VCM_ADDR; - msg[0].flags = 0; - msg[0].len = 0x01; - msg[0].buf = &buf[0]; - - msg[1].addr = 0x0c; - msg[1].flags = I2C_M_RD; - msg[1].len = 0x01; - msg[1].buf = &buf[1]; - *val = 0; - if (i2c_transfer(client->adapter, msg, 2) != 2) - return -EIO; - *val = buf[1]; - return 0; -} - -static const u32 ov5693_embedded_effective_size = 28; - -/* i2c read/write stuff */ -static int ov5693_read_reg(struct i2c_client *client, - u16 data_length, u16 reg, u16 *val) -{ - int err; - struct i2c_msg msg[2]; - unsigned char data[6]; - - if (!client->adapter) { - dev_err(&client->dev, "%s error, no client->adapter\n", - __func__); - return -ENODEV; - } - - if (data_length != OV5693_8BIT && data_length != OV5693_16BIT - && data_length != OV5693_32BIT) { - dev_err(&client->dev, "%s error, invalid data length\n", - __func__); - return -EINVAL; - } - - memset(msg, 0, sizeof(msg)); - - msg[0].addr = client->addr; - msg[0].flags = 0; - msg[0].len = I2C_MSG_LENGTH; - msg[0].buf = data; - - /* high byte goes out first */ - data[0] = (u8)(reg >> 8); - data[1] = (u8)(reg & 0xff); - - msg[1].addr = client->addr; - msg[1].len = data_length; - msg[1].flags = I2C_M_RD; - msg[1].buf = data; - - err = i2c_transfer(client->adapter, msg, 2); - if (err != 2) { - if (err >= 0) - err = -EIO; - dev_err(&client->dev, - "read from offset 0x%x error %d", reg, err); - return err; - } - - *val = 0; - /* high byte comes first */ - if (data_length == OV5693_8BIT) - *val = (u8)data[0]; - else if (data_length == OV5693_16BIT) - *val = be16_to_cpu(*(__be16 *)&data[0]); - else - *val = be32_to_cpu(*(__be32 *)&data[0]); - - return 0; -} - -static int ov5693_i2c_write(struct i2c_client *client, u16 len, u8 *data) -{ - struct i2c_msg msg; - const int num_msg = 1; - int ret; - - msg.addr = client->addr; - msg.flags = 0; - msg.len = len; - msg.buf = data; - ret = i2c_transfer(client->adapter, &msg, 1); - - return ret == num_msg ? 0 : -EIO; -} - -static int vcm_dw_i2c_write(struct i2c_client *client, u16 data) -{ - struct i2c_msg msg; - const int num_msg = 1; - int ret; - __be16 val; - - val = cpu_to_be16(data); - msg.addr = VCM_ADDR; - msg.flags = 0; - msg.len = OV5693_16BIT; - msg.buf = (void *)&val; - - ret = i2c_transfer(client->adapter, &msg, 1); - - return ret == num_msg ? 0 : -EIO; -} - -/* - * Theory: per datasheet, the two VCMs both allow for a 2-byte read. - * The DW9714 doesn't actually specify what this does (it has a - * two-byte write-only protocol, but specifies the read sequence as - * legal), but it returns the same data (zeroes) always, after an - * undocumented initial NAK. The AD5823 has a one-byte address - * register to which all writes go, and subsequent reads will cycle - * through the 8 bytes of registers. Notably, the default values (the - * device is always power-cycled affirmatively, so we can rely on - * these) in AD5823 are not pairwise repetitions of the same 16 bit - * word. So all we have to do is sequentially read two bytes at a - * time and see if we detect a difference in any of the first four - * pairs. - */ -static int vcm_detect(struct i2c_client *client) -{ - int i, ret; - struct i2c_msg msg; - u16 data0 = 0, data; - - for (i = 0; i < 4; i++) { - msg.addr = VCM_ADDR; - msg.flags = I2C_M_RD; - msg.len = sizeof(data); - msg.buf = (u8 *)&data; - ret = i2c_transfer(client->adapter, &msg, 1); - - /* - * DW9714 always fails the first read and returns - * zeroes for subsequent ones - */ - if (i == 0 && ret == -EREMOTEIO) { - data0 = 0; - continue; - } - - if (i == 0) - data0 = data; - - if (data != data0) - return VCM_AD5823; - } - return ret == 1 ? VCM_DW9714 : ret; -} - -static int ov5693_write_reg(struct i2c_client *client, u16 data_length, - u16 reg, u16 val) -{ - int ret; - unsigned char data[4] = {0}; - __be16 *wreg = (void *)data; - const u16 len = data_length + sizeof(u16); /* 16-bit address + data */ - - if (data_length != OV5693_8BIT && data_length != OV5693_16BIT) { - dev_err(&client->dev, - "%s error, invalid data_length\n", __func__); - return -EINVAL; - } - - /* high byte goes out first */ - *wreg = cpu_to_be16(reg); - - if (data_length == OV5693_8BIT) { - data[2] = (u8)(val); - } else { - /* OV5693_16BIT */ - __be16 *wdata = (void *)&data[2]; - - *wdata = cpu_to_be16(val); - } - - ret = ov5693_i2c_write(client, len, data); - if (ret) - dev_err(&client->dev, - "write error: wrote 0x%x to offset 0x%x error %d", - val, reg, ret); - - return ret; -} - -/* - * ov5693_write_reg_array - Initializes a list of OV5693 registers - * @client: i2c driver client structure - * @reglist: list of registers to be written - * - * This function initializes a list of registers. When consecutive addresses - * are found in a row on the list, this function creates a buffer and sends - * consecutive data in a single i2c_transfer(). - * - * __ov5693_flush_reg_array, __ov5693_buf_reg_array() and - * __ov5693_write_reg_is_consecutive() are internal functions to - * ov5693_write_reg_array_fast() and should be not used anywhere else. - * - */ - -static int __ov5693_flush_reg_array(struct i2c_client *client, - struct ov5693_write_ctrl *ctrl) -{ - u16 size; - __be16 *reg = (void *)&ctrl->buffer.addr; - - if (ctrl->index == 0) - return 0; - - size = sizeof(u16) + ctrl->index; /* 16-bit address + data */ - - *reg = cpu_to_be16(ctrl->buffer.addr); - ctrl->index = 0; - - return ov5693_i2c_write(client, size, (u8 *)reg); -} - -static int __ov5693_buf_reg_array(struct i2c_client *client, - struct ov5693_write_ctrl *ctrl, - const struct ov5693_reg *next) -{ - int size; - __be16 *data16; - - switch (next->type) { - case OV5693_8BIT: - size = 1; - ctrl->buffer.data[ctrl->index] = (u8)next->val; - break; - case OV5693_16BIT: - size = 2; - - data16 = (void *)&ctrl->buffer.data[ctrl->index]; - *data16 = cpu_to_be16((u16)next->val); - break; - default: - return -EINVAL; - } - - /* When first item is added, we need to store its starting address */ - if (ctrl->index == 0) - ctrl->buffer.addr = next->reg; - - ctrl->index += size; - - /* - * Buffer cannot guarantee free space for u32? Better flush it to avoid - * possible lack of memory for next item. - */ - if (ctrl->index + sizeof(u16) >= OV5693_MAX_WRITE_BUF_SIZE) - return __ov5693_flush_reg_array(client, ctrl); - - return 0; -} - -static int __ov5693_write_reg_is_consecutive(struct i2c_client *client, - struct ov5693_write_ctrl *ctrl, - const struct ov5693_reg *next) -{ - if (ctrl->index == 0) - return 1; - - return ctrl->buffer.addr + ctrl->index == next->reg; -} - -static int ov5693_write_reg_array(struct i2c_client *client, - const struct ov5693_reg *reglist) -{ - const struct ov5693_reg *next = reglist; - struct ov5693_write_ctrl ctrl; - int err; - - ctrl.index = 0; - for (; next->type != OV5693_TOK_TERM; next++) { - switch (next->type & OV5693_TOK_MASK) { - case OV5693_TOK_DELAY: - err = __ov5693_flush_reg_array(client, &ctrl); - if (err) - return err; - msleep(next->val); - break; - default: - /* - * If next address is not consecutive, data needs to be - * flushed before proceed. - */ - if (!__ov5693_write_reg_is_consecutive(client, &ctrl, - next)) { - err = __ov5693_flush_reg_array(client, &ctrl); - if (err) - return err; - } - err = __ov5693_buf_reg_array(client, &ctrl, next); - if (err) { - dev_err(&client->dev, - "%s: write error, aborted\n", - __func__); - return err; - } - break; - } - } - - return __ov5693_flush_reg_array(client, &ctrl); -} - -static long __ov5693_set_exposure(struct v4l2_subdev *sd, int coarse_itg, - int gain, int digitgain) - -{ - struct i2c_client *client = v4l2_get_subdevdata(sd); - struct ov5693_device *dev = to_ov5693_sensor(sd); - u16 vts, hts; - int ret, exp_val; - - hts = ov5693_res[dev->fmt_idx].pixels_per_line; - vts = ov5693_res[dev->fmt_idx].lines_per_frame; - /* - * If coarse_itg is larger than 1<<15, can not write to reg directly. - * The way is to write coarse_itg/2 to the reg, meanwhile write 2*hts - * to the reg. - */ - if (coarse_itg > (1 << 15)) { - hts = hts * 2; - coarse_itg = (int)coarse_itg / 2; - } - /* group hold */ - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_GROUP_ACCESS, 0x00); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_GROUP_ACCESS); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_TIMING_HTS_H, (hts >> 8) & 0xFF); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_TIMING_HTS_H); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_TIMING_HTS_L, hts & 0xFF); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_TIMING_HTS_L); - return ret; - } - /* Increase the VTS to match exposure + MARGIN */ - if (coarse_itg > vts - OV5693_INTEGRATION_TIME_MARGIN) - vts = (u16)coarse_itg + OV5693_INTEGRATION_TIME_MARGIN; - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_TIMING_VTS_H, (vts >> 8) & 0xFF); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_TIMING_VTS_H); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_TIMING_VTS_L, vts & 0xFF); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_TIMING_VTS_L); - return ret; - } - - /* set exposure */ - - /* Lower four bit should be 0*/ - exp_val = coarse_itg << 4; - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_EXPOSURE_L, exp_val & 0xFF); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_EXPOSURE_L); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_EXPOSURE_M, (exp_val >> 8) & 0xFF); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_EXPOSURE_M); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_EXPOSURE_H, (exp_val >> 16) & 0x0F); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_EXPOSURE_H); - return ret; - } - - /* Analog gain */ - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_AGC_L, gain & 0xff); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_AGC_L); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_AGC_H, (gain >> 8) & 0xff); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_AGC_H); - return ret; - } - - /* Digital gain */ - if (digitgain) { - ret = ov5693_write_reg(client, OV5693_16BIT, - OV5693_MWB_RED_GAIN_H, digitgain); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_MWB_RED_GAIN_H); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_16BIT, - OV5693_MWB_GREEN_GAIN_H, digitgain); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_MWB_RED_GAIN_H); - return ret; - } - - ret = ov5693_write_reg(client, OV5693_16BIT, - OV5693_MWB_BLUE_GAIN_H, digitgain); - if (ret) { - dev_err(&client->dev, "%s: write %x error, aborted\n", - __func__, OV5693_MWB_RED_GAIN_H); - return ret; - } - } - - /* End group */ - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_GROUP_ACCESS, 0x10); - if (ret) - return ret; - - /* Delay launch group */ - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_GROUP_ACCESS, 0xa0); - if (ret) - return ret; - return ret; -} - -static int ov5693_set_exposure(struct v4l2_subdev *sd, int exposure, - int gain, int digitgain) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - int ret; - - mutex_lock(&dev->input_lock); - ret = __ov5693_set_exposure(sd, exposure, gain, digitgain); - mutex_unlock(&dev->input_lock); - - return ret; -} - -static long ov5693_s_exposure(struct v4l2_subdev *sd, - struct atomisp_exposure *exposure) -{ - u16 coarse_itg = exposure->integration_time[0]; - u16 analog_gain = exposure->gain[0]; - u16 digital_gain = exposure->gain[1]; - - /* we should not accept the invalid value below */ - if (analog_gain == 0) { - struct i2c_client *client = v4l2_get_subdevdata(sd); - - v4l2_err(client, "%s: invalid value\n", __func__); - return -EINVAL; - } - return ov5693_set_exposure(sd, coarse_itg, analog_gain, digital_gain); -} - -static int ov5693_read_otp_reg_array(struct i2c_client *client, u16 size, - u16 addr, u8 *buf) -{ - u16 index; - int ret; - u16 *pVal = NULL; - - for (index = 0; index <= size; index++) { - pVal = (u16 *)(buf + index); - ret = - ov5693_read_reg(client, OV5693_8BIT, addr + index, - pVal); - if (ret) - return ret; - } - - return 0; -} - -static int __ov5693_otp_read(struct v4l2_subdev *sd, u8 *buf) -{ - struct i2c_client *client = v4l2_get_subdevdata(sd); - struct ov5693_device *dev = to_ov5693_sensor(sd); - int ret; - int i; - u8 *b = buf; - - dev->otp_size = 0; - for (i = 1; i < OV5693_OTP_BANK_MAX; i++) { - /*set bank NO and OTP read mode. */ - ret = ov5693_write_reg(client, OV5693_8BIT, OV5693_OTP_BANK_REG, - (i | 0xc0)); //[7:6] 2'b11 [5:0] bank no - if (ret) { - dev_err(&client->dev, "failed to prepare OTP page\n"); - return ret; - } - //pr_debug("write 0x%x->0x%x\n",OV5693_OTP_BANK_REG,(i|0xc0)); - - /*enable read */ - ret = ov5693_write_reg(client, OV5693_8BIT, OV5693_OTP_READ_REG, - OV5693_OTP_MODE_READ); // enable :1 - if (ret) { - dev_err(&client->dev, - "failed to set OTP reading mode page"); - return ret; - } - //pr_debug("write 0x%x->0x%x\n",OV5693_OTP_READ_REG,OV5693_OTP_MODE_READ); - - /* Reading the OTP data array */ - ret = ov5693_read_otp_reg_array(client, OV5693_OTP_BANK_SIZE, - OV5693_OTP_START_ADDR, - b); - if (ret) { - dev_err(&client->dev, "failed to read OTP data\n"); - return ret; - } - - //pr_debug("BANK[%2d] %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x\n", i, *b, *(b+1), *(b+2), *(b+3), *(b+4), *(b+5), *(b+6), *(b+7), *(b+8), *(b+9), *(b+10), *(b+11), *(b+12), *(b+13), *(b+14), *(b+15)); - - //Intel OTP map, try to read 320byts first. - if (i == 21) { - if ((*b) == 0) { - dev->otp_size = 320; - break; - } else { - b = buf; - continue; - } - } else if (i == - 24) { //if the first 320bytes data doesn't not exist, try to read the next 32bytes data. - if ((*b) == 0) { - dev->otp_size = 32; - break; - } else { - b = buf; - continue; - } - } else if (i == - 27) { //if the prvious 32bytes data doesn't exist, try to read the next 32bytes data again. - if ((*b) == 0) { - dev->otp_size = 32; - break; - } else { - dev->otp_size = 0; // no OTP data. - break; - } - } - - b = b + OV5693_OTP_BANK_SIZE; - } - return 0; -} - -/* - * Read otp data and store it into a kmalloced buffer. - * The caller must kfree the buffer when no more needed. - * @size: set to the size of the returned otp data. - */ -static void *ov5693_otp_read(struct v4l2_subdev *sd) -{ - struct i2c_client *client = v4l2_get_subdevdata(sd); - u8 *buf; - int ret; - - buf = devm_kzalloc(&client->dev, (OV5693_OTP_DATA_SIZE + 16), GFP_KERNEL); - if (!buf) - return ERR_PTR(-ENOMEM); - - //otp valid after mipi on and sw stream on - ret = ov5693_write_reg(client, OV5693_8BIT, OV5693_FRAME_OFF_NUM, 0x00); - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_SW_STREAM, OV5693_START_STREAMING); - - ret = __ov5693_otp_read(sd, buf); - - //mipi off and sw stream off after otp read - ret = ov5693_write_reg(client, OV5693_8BIT, OV5693_FRAME_OFF_NUM, 0x0f); - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_SW_STREAM, OV5693_STOP_STREAMING); - - /* Driver has failed to find valid data */ - if (ret) { - dev_err(&client->dev, "sensor found no valid OTP data\n"); - return ERR_PTR(ret); - } - - return buf; -} - -static long ov5693_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg) -{ - switch (cmd) { - case ATOMISP_IOC_S_EXPOSURE: - return ov5693_s_exposure(sd, arg); - default: - return -EINVAL; - } - return 0; -} - -/* - * This returns the exposure time being used. This should only be used - * for filling in EXIF data, not for actual image processing. - */ -static int ov5693_q_exposure(struct v4l2_subdev *sd, s32 *value) -{ - struct i2c_client *client = v4l2_get_subdevdata(sd); - u16 reg_v, reg_v2; - int ret; - - /* get exposure */ - ret = ov5693_read_reg(client, OV5693_8BIT, - OV5693_EXPOSURE_L, - ®_v); - if (ret) - goto err; - - ret = ov5693_read_reg(client, OV5693_8BIT, - OV5693_EXPOSURE_M, - ®_v2); - if (ret) - goto err; - - reg_v += reg_v2 << 8; - ret = ov5693_read_reg(client, OV5693_8BIT, - OV5693_EXPOSURE_H, - ®_v2); - if (ret) - goto err; - - *value = reg_v + (((u32)reg_v2 << 16)); -err: - return ret; -} - -static int ad5823_t_focus_vcm(struct v4l2_subdev *sd, u16 val) -{ - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret; - u8 vcm_code; - - ret = ad5823_i2c_read(client, AD5823_REG_VCM_CODE_MSB, &vcm_code); - if (ret) - return ret; - - /* set reg VCM_CODE_MSB Bit[1:0] */ - vcm_code = (vcm_code & VCM_CODE_MSB_MASK) | - ((val >> 8) & ~VCM_CODE_MSB_MASK); - ret = ad5823_i2c_write(client, AD5823_REG_VCM_CODE_MSB, vcm_code); - if (ret) - return ret; - - /* set reg VCM_CODE_LSB Bit[7:0] */ - ret = ad5823_i2c_write(client, AD5823_REG_VCM_CODE_LSB, (val & 0xff)); - if (ret) - return ret; - - /* set required vcm move time */ - vcm_code = AD5823_RESONANCE_PERIOD / AD5823_RESONANCE_COEF - - AD5823_HIGH_FREQ_RANGE; - ret = ad5823_i2c_write(client, AD5823_REG_VCM_MOVE_TIME, vcm_code); - - return ret; -} - -static int ad5823_t_focus_abs(struct v4l2_subdev *sd, s32 value) -{ - value = min(value, AD5823_MAX_FOCUS_POS); - return ad5823_t_focus_vcm(sd, value); -} - -static int ov5693_t_focus_abs(struct v4l2_subdev *sd, s32 value) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret = 0; - - dev_dbg(&client->dev, "%s: FOCUS_POS: 0x%x\n", __func__, value); - value = clamp(value, 0, OV5693_VCM_MAX_FOCUS_POS); - if (dev->vcm == VCM_DW9714) { - if (dev->vcm_update) { - ret = vcm_dw_i2c_write(client, VCM_PROTECTION_OFF); - if (ret) - return ret; - ret = vcm_dw_i2c_write(client, DIRECT_VCM); - if (ret) - return ret; - ret = vcm_dw_i2c_write(client, VCM_PROTECTION_ON); - if (ret) - return ret; - dev->vcm_update = false; - } - ret = vcm_dw_i2c_write(client, - vcm_val(value, VCM_DEFAULT_S)); - } else if (dev->vcm == VCM_AD5823) { - ad5823_t_focus_abs(sd, value); - } - if (ret == 0) { - dev->number_of_steps = value - dev->focus; - dev->focus = value; - dev->timestamp_t_focus_abs = ktime_get(); - } else - dev_err(&client->dev, - "%s: i2c failed. ret %d\n", __func__, ret); - - return ret; -} - -static int ov5693_t_focus_rel(struct v4l2_subdev *sd, s32 value) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - - return ov5693_t_focus_abs(sd, dev->focus + value); -} - -#define DELAY_PER_STEP_NS 1000000 -#define DELAY_MAX_PER_STEP_NS (1000000 * 1023) -static int ov5693_q_focus_status(struct v4l2_subdev *sd, s32 *value) -{ - u32 status = 0; - struct ov5693_device *dev = to_ov5693_sensor(sd); - ktime_t temptime; - ktime_t timedelay = ns_to_ktime(min_t(u32, - abs(dev->number_of_steps) * DELAY_PER_STEP_NS, - DELAY_MAX_PER_STEP_NS)); - - temptime = ktime_sub(ktime_get(), (dev->timestamp_t_focus_abs)); - if (ktime_compare(temptime, timedelay) <= 0) { - status |= ATOMISP_FOCUS_STATUS_MOVING; - status |= ATOMISP_FOCUS_HP_IN_PROGRESS; - } else { - status |= ATOMISP_FOCUS_STATUS_ACCEPTS_NEW_MOVE; - status |= ATOMISP_FOCUS_HP_COMPLETE; - } - - *value = status; - - return 0; -} - -static int ov5693_q_focus_abs(struct v4l2_subdev *sd, s32 *value) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - s32 val; - - ov5693_q_focus_status(sd, &val); - - if (val & ATOMISP_FOCUS_STATUS_MOVING) - *value = dev->focus - dev->number_of_steps; - else - *value = dev->focus; - - return 0; -} - -static int ov5693_t_vcm_slew(struct v4l2_subdev *sd, s32 value) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - - dev->number_of_steps = value; - dev->vcm_update = true; - return 0; -} - -static int ov5693_t_vcm_timing(struct v4l2_subdev *sd, s32 value) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - - dev->number_of_steps = value; - dev->vcm_update = true; - return 0; -} - -static int ov5693_s_ctrl(struct v4l2_ctrl *ctrl) -{ - struct ov5693_device *dev = - container_of(ctrl->handler, struct ov5693_device, ctrl_handler); - struct i2c_client *client = v4l2_get_subdevdata(&dev->sd); - int ret = 0; - - switch (ctrl->id) { - case V4L2_CID_FOCUS_ABSOLUTE: - dev_dbg(&client->dev, "%s: CID_FOCUS_ABSOLUTE:%d.\n", - __func__, ctrl->val); - ret = ov5693_t_focus_abs(&dev->sd, ctrl->val); - break; - case V4L2_CID_FOCUS_RELATIVE: - dev_dbg(&client->dev, "%s: CID_FOCUS_RELATIVE:%d.\n", - __func__, ctrl->val); - ret = ov5693_t_focus_rel(&dev->sd, ctrl->val); - break; - case V4L2_CID_VCM_SLEW: - ret = ov5693_t_vcm_slew(&dev->sd, ctrl->val); - break; - case V4L2_CID_VCM_TIMING: - ret = ov5693_t_vcm_timing(&dev->sd, ctrl->val); - break; - default: - ret = -EINVAL; - } - return ret; -} - -static int ov5693_g_volatile_ctrl(struct v4l2_ctrl *ctrl) -{ - struct ov5693_device *dev = - container_of(ctrl->handler, struct ov5693_device, ctrl_handler); - int ret = 0; - - switch (ctrl->id) { - case V4L2_CID_EXPOSURE_ABSOLUTE: - ret = ov5693_q_exposure(&dev->sd, &ctrl->val); - break; - case V4L2_CID_FOCUS_ABSOLUTE: - ret = ov5693_q_focus_abs(&dev->sd, &ctrl->val); - break; - case V4L2_CID_FOCUS_STATUS: - ret = ov5693_q_focus_status(&dev->sd, &ctrl->val); - break; - default: - ret = -EINVAL; - } - - return ret; -} - -static const struct v4l2_ctrl_ops ctrl_ops = { - .s_ctrl = ov5693_s_ctrl, - .g_volatile_ctrl = ov5693_g_volatile_ctrl -}; - -static const struct v4l2_ctrl_config ov5693_controls[] = { - { - .ops = &ctrl_ops, - .id = V4L2_CID_EXPOSURE_ABSOLUTE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "exposure", - .min = 0x0, - .max = 0xffff, - .step = 0x01, - .def = 0x00, - .flags = 0, - }, - { - .ops = &ctrl_ops, - .id = V4L2_CID_FOCUS_ABSOLUTE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "focus move absolute", - .min = 0, - .max = OV5693_VCM_MAX_FOCUS_POS, - .step = 1, - .def = 0, - .flags = 0, - }, - { - .ops = &ctrl_ops, - .id = V4L2_CID_FOCUS_RELATIVE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "focus move relative", - .min = OV5693_VCM_MAX_FOCUS_NEG, - .max = OV5693_VCM_MAX_FOCUS_POS, - .step = 1, - .def = 0, - .flags = 0, - }, - { - .ops = &ctrl_ops, - .id = V4L2_CID_FOCUS_STATUS, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "focus status", - .min = 0, - .max = 100, /* allow enum to grow in the future */ - .step = 1, - .def = 0, - .flags = 0, - }, - { - .ops = &ctrl_ops, - .id = V4L2_CID_VCM_SLEW, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "vcm slew", - .min = 0, - .max = OV5693_VCM_SLEW_STEP_MAX, - .step = 1, - .def = 0, - .flags = 0, - }, - { - .ops = &ctrl_ops, - .id = V4L2_CID_VCM_TIMING, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "vcm step time", - .min = 0, - .max = OV5693_VCM_SLEW_TIME_MAX, - .step = 1, - .def = 0, - .flags = 0, - }, -}; - -static int ov5693_init(struct v4l2_subdev *sd) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret; - - pr_info("%s\n", __func__); - mutex_lock(&dev->input_lock); - dev->vcm_update = false; - - if (dev->vcm == VCM_AD5823) { - ret = vcm_ad_i2c_wr8(client, 0x01, 0x01); /* vcm init test */ - if (ret) - dev_err(&client->dev, - "vcm reset failed\n"); - /*change the mode*/ - ret = ad5823_i2c_write(client, AD5823_REG_VCM_CODE_MSB, - AD5823_RING_CTRL_ENABLE); - if (ret) - dev_err(&client->dev, - "vcm enable ringing failed\n"); - ret = ad5823_i2c_write(client, AD5823_REG_MODE, - AD5823_ARC_RES1); - if (ret) - dev_err(&client->dev, - "vcm change mode failed\n"); - } - - /*change initial focus value for ad5823*/ - if (dev->vcm == VCM_AD5823) { - dev->focus = AD5823_INIT_FOCUS_POS; - ov5693_t_focus_abs(sd, AD5823_INIT_FOCUS_POS); - } else { - dev->focus = 0; - ov5693_t_focus_abs(sd, 0); - } - - mutex_unlock(&dev->input_lock); - - return 0; -} - -static int power_ctrl(struct v4l2_subdev *sd, bool flag) -{ - int ret; - struct ov5693_device *dev = to_ov5693_sensor(sd); - - if (!dev || !dev->platform_data) - return -ENODEV; - - /* - * This driver assumes "internal DVDD, PWDNB tied to DOVDD". - * In this set up only gpio0 (XSHUTDN) should be available - * but in some products (for example ECS) gpio1 (PWDNB) is - * also available. If gpio1 is available we emulate it being - * tied to DOVDD here. - */ - if (flag) { - ret = dev->platform_data->v2p8_ctrl(sd, 1); - dev->platform_data->gpio1_ctrl(sd, 1); - if (ret == 0) { - ret = dev->platform_data->v1p8_ctrl(sd, 1); - if (ret) { - dev->platform_data->gpio1_ctrl(sd, 0); - ret = dev->platform_data->v2p8_ctrl(sd, 0); - } - } - } else { - dev->platform_data->gpio1_ctrl(sd, 0); - ret = dev->platform_data->v1p8_ctrl(sd, 0); - ret |= dev->platform_data->v2p8_ctrl(sd, 0); - } - - return ret; -} - -static int gpio_ctrl(struct v4l2_subdev *sd, bool flag) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - - if (!dev || !dev->platform_data) - return -ENODEV; - - return dev->platform_data->gpio0_ctrl(sd, flag); -} - -static int __power_up(struct v4l2_subdev *sd) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret; - - if (!dev->platform_data) { - dev_err(&client->dev, - "no camera_sensor_platform_data"); - return -ENODEV; - } - - /* power control */ - ret = power_ctrl(sd, 1); - if (ret) - goto fail_power; - - /* according to DS, at least 5ms is needed between DOVDD and PWDN */ - /* add this delay time to 10~11ms*/ - usleep_range(10000, 11000); - - /* gpio ctrl */ - ret = gpio_ctrl(sd, 1); - if (ret) { - ret = gpio_ctrl(sd, 1); - if (ret) - goto fail_power; - } - - /* flis clock control */ - ret = dev->platform_data->flisclk_ctrl(sd, 1); - if (ret) - goto fail_clk; - - __cci_delay(up_delay); - - return 0; - -fail_clk: - gpio_ctrl(sd, 0); -fail_power: - power_ctrl(sd, 0); - dev_err(&client->dev, "sensor power-up failed\n"); - - return ret; -} - -static int power_down(struct v4l2_subdev *sd) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret = 0; - - dev->focus = OV5693_INVALID_CONFIG; - if (!dev->platform_data) { - dev_err(&client->dev, - "no camera_sensor_platform_data"); - return -ENODEV; - } - - ret = dev->platform_data->flisclk_ctrl(sd, 0); - if (ret) - dev_err(&client->dev, "flisclk failed\n"); - - /* gpio ctrl */ - ret = gpio_ctrl(sd, 0); - if (ret) { - ret = gpio_ctrl(sd, 0); - if (ret) - dev_err(&client->dev, "gpio failed 2\n"); - } - - /* power control */ - ret = power_ctrl(sd, 0); - if (ret) - dev_err(&client->dev, "vprog failed.\n"); - - return ret; -} - -static int power_up(struct v4l2_subdev *sd) -{ - static const int retry_count = 4; - int i, ret; - - for (i = 0; i < retry_count; i++) { - ret = __power_up(sd); - if (!ret) - return 0; - - power_down(sd); - } - return ret; -} - -static int ov5693_s_power(struct v4l2_subdev *sd, int on) -{ - int ret; - - pr_info("%s: on %d\n", __func__, on); - if (on == 0) - return power_down(sd); - else { - ret = power_up(sd); - if (!ret) { - ret = ov5693_init(sd); - /* restore settings */ - ov5693_res = ov5693_res_preview; - N_RES = N_RES_PREVIEW; - } - } - return ret; -} - -/* - * distance - calculate the distance - * @res: resolution - * @w: width - * @h: height - * - * Get the gap between res_w/res_h and w/h. - * distance = (res_w/res_h - w/h) / (w/h) * 8192 - * res->width/height smaller than w/h wouldn't be considered. - * The gap of ratio larger than 1/8 wouldn't be considered. - * Returns the value of gap or -1 if fail. - */ -#define LARGEST_ALLOWED_RATIO_MISMATCH 1024 -static int distance(struct ov5693_resolution *res, u32 w, u32 h) -{ - int ratio; - int distance; - - if (w == 0 || h == 0 || - res->width < w || res->height < h) - return -1; - - ratio = res->width << 13; - ratio /= w; - ratio *= h; - ratio /= res->height; - - distance = abs(ratio - 8192); - - if (distance > LARGEST_ALLOWED_RATIO_MISMATCH) - return -1; - - return distance; -} - -/* Return the nearest higher resolution index - * Firstly try to find the approximate aspect ratio resolution - * If we find multiple same AR resolutions, choose the - * minimal size. - */ -static int nearest_resolution_index(int w, int h) -{ - int i; - int idx = -1; - int dist; - int min_dist = INT_MAX; - int min_res_w = INT_MAX; - struct ov5693_resolution *tmp_res = NULL; - - for (i = 0; i < N_RES; i++) { - tmp_res = &ov5693_res[i]; - dist = distance(tmp_res, w, h); - if (dist == -1) - continue; - if (dist < min_dist) { - min_dist = dist; - idx = i; - min_res_w = ov5693_res[i].width; - continue; - } - if (dist == min_dist && ov5693_res[i].width < min_res_w) - idx = i; - } - - return idx; -} - -static int get_resolution_index(int w, int h) -{ - int i; - - for (i = 0; i < N_RES; i++) { - if (w != ov5693_res[i].width) - continue; - if (h != ov5693_res[i].height) - continue; - - return i; - } - - return -1; -} - -/* TODO: remove it. */ -static int startup(struct v4l2_subdev *sd) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret = 0; - - ret = ov5693_write_reg(client, OV5693_8BIT, - OV5693_SW_RESET, 0x01); - if (ret) { - dev_err(&client->dev, "ov5693 reset err.\n"); - return ret; - } - - ret = ov5693_write_reg_array(client, ov5693_global_setting); - if (ret) { - dev_err(&client->dev, "ov5693 write register err.\n"); - return ret; - } - - ret = ov5693_write_reg_array(client, ov5693_res[dev->fmt_idx].regs); - if (ret) { - dev_err(&client->dev, "ov5693 write register err.\n"); - return ret; - } - - return ret; -} - -static int ov5693_set_fmt(struct v4l2_subdev *sd, - struct v4l2_subdev_state *sd_state, - struct v4l2_subdev_format *format) -{ - struct v4l2_mbus_framefmt *fmt = &format->format; - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - struct camera_mipi_info *ov5693_info = NULL; - int ret = 0; - int idx; - - if (format->pad) - return -EINVAL; - if (!fmt) - return -EINVAL; - ov5693_info = v4l2_get_subdev_hostdata(sd); - if (!ov5693_info) - return -EINVAL; - - mutex_lock(&dev->input_lock); - idx = nearest_resolution_index(fmt->width, fmt->height); - if (idx == -1) { - /* return the largest resolution */ - fmt->width = ov5693_res[N_RES - 1].width; - fmt->height = ov5693_res[N_RES - 1].height; - } else { - fmt->width = ov5693_res[idx].width; - fmt->height = ov5693_res[idx].height; - } - - fmt->code = MEDIA_BUS_FMT_SBGGR10_1X10; - if (format->which == V4L2_SUBDEV_FORMAT_TRY) { - sd_state->pads->try_fmt = *fmt; - mutex_unlock(&dev->input_lock); - return 0; - } - - dev->fmt_idx = get_resolution_index(fmt->width, fmt->height); - if (dev->fmt_idx == -1) { - dev_err(&client->dev, "get resolution fail\n"); - mutex_unlock(&dev->input_lock); - return -EINVAL; - } - - ret = startup(sd); - if (ret) { - int i = 0; - - dev_err(&client->dev, "ov5693 startup err, retry to power up\n"); - for (i = 0; i < OV5693_POWER_UP_RETRY_NUM; i++) { - dev_err(&client->dev, - "ov5693 retry to power up %d/%d times, result: ", - i + 1, OV5693_POWER_UP_RETRY_NUM); - power_down(sd); - ret = power_up(sd); - if (!ret) { - mutex_unlock(&dev->input_lock); - ov5693_init(sd); - mutex_lock(&dev->input_lock); - } else { - dev_err(&client->dev, "power up failed, continue\n"); - continue; - } - ret = startup(sd); - if (ret) { - dev_err(&client->dev, " startup FAILED!\n"); - } else { - dev_err(&client->dev, " startup SUCCESS!\n"); - break; - } - } - } - - /* - * After sensor settings are set to HW, sometimes stream is started. - * This would cause ISP timeout because ISP is not ready to receive - * data yet. So add stop streaming here. - */ - ret = ov5693_write_reg(client, OV5693_8BIT, OV5693_SW_STREAM, - OV5693_STOP_STREAMING); - if (ret) - dev_warn(&client->dev, "ov5693 stream off err\n"); - - ov5693_info->metadata_width = fmt->width * 10 / 8; - ov5693_info->metadata_height = 1; - ov5693_info->metadata_effective_width = &ov5693_embedded_effective_size; - - mutex_unlock(&dev->input_lock); - return ret; -} - -static int ov5693_get_fmt(struct v4l2_subdev *sd, - struct v4l2_subdev_state *sd_state, - struct v4l2_subdev_format *format) -{ - struct v4l2_mbus_framefmt *fmt = &format->format; - struct ov5693_device *dev = to_ov5693_sensor(sd); - - if (format->pad) - return -EINVAL; - - if (!fmt) - return -EINVAL; - - fmt->width = ov5693_res[dev->fmt_idx].width; - fmt->height = ov5693_res[dev->fmt_idx].height; - fmt->code = MEDIA_BUS_FMT_SBGGR10_1X10; - - return 0; -} - -static int ov5693_detect(struct i2c_client *client) -{ - struct i2c_adapter *adapter = client->adapter; - u16 high, low; - int ret; - u16 id; - u8 revision; - - if (!i2c_check_functionality(adapter, I2C_FUNC_I2C)) - return -ENODEV; - - ret = ov5693_read_reg(client, OV5693_8BIT, - OV5693_SC_CMMN_CHIP_ID_H, &high); - if (ret) { - dev_err(&client->dev, "sensor_id_high = 0x%x\n", high); - return -ENODEV; - } - ret = ov5693_read_reg(client, OV5693_8BIT, - OV5693_SC_CMMN_CHIP_ID_L, &low); - if (ret) - return ret; - id = ((((u16)high) << 8) | (u16)low); - - if (id != OV5693_ID) { - dev_err(&client->dev, "sensor ID error 0x%x\n", id); - return -ENODEV; - } - - ret = ov5693_read_reg(client, OV5693_8BIT, - OV5693_SC_CMMN_SUB_ID, &high); - revision = (u8)high & 0x0f; - - dev_dbg(&client->dev, "sensor_revision = 0x%x\n", revision); - dev_dbg(&client->dev, "detect ov5693 success\n"); - return 0; -} - -static int ov5693_s_stream(struct v4l2_subdev *sd, int enable) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret; - - mutex_lock(&dev->input_lock); - - ret = ov5693_write_reg(client, OV5693_8BIT, OV5693_SW_STREAM, - enable ? OV5693_START_STREAMING : - OV5693_STOP_STREAMING); - - mutex_unlock(&dev->input_lock); - - return ret; -} - -static int ov5693_s_config(struct v4l2_subdev *sd, - int irq, void *platform_data) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - struct i2c_client *client = v4l2_get_subdevdata(sd); - int ret = 0; - - if (!platform_data) - return -ENODEV; - - dev->platform_data = - (struct camera_sensor_platform_data *)platform_data; - - mutex_lock(&dev->input_lock); - /* power off the module, then power on it in future - * as first power on by board may not fulfill the - * power on sequqence needed by the module - */ - ret = power_down(sd); - if (ret) { - dev_err(&client->dev, "ov5693 power-off err.\n"); - goto fail_power_off; - } - - ret = power_up(sd); - if (ret) { - dev_err(&client->dev, "ov5693 power-up err.\n"); - goto fail_power_on; - } - - if (!dev->vcm) - dev->vcm = vcm_detect(client); - - ret = dev->platform_data->csi_cfg(sd, 1); - if (ret) - goto fail_csi_cfg; - - /* config & detect sensor */ - ret = ov5693_detect(client); - if (ret) { - dev_err(&client->dev, "ov5693_detect err s_config.\n"); - goto fail_csi_cfg; - } - - dev->otp_data = ov5693_otp_read(sd); - - /* turn off sensor, after probed */ - ret = power_down(sd); - if (ret) { - dev_err(&client->dev, "ov5693 power-off err.\n"); - goto fail_csi_cfg; - } - mutex_unlock(&dev->input_lock); - - return ret; - -fail_csi_cfg: - dev->platform_data->csi_cfg(sd, 0); -fail_power_on: - power_down(sd); - dev_err(&client->dev, "sensor power-gating failed\n"); -fail_power_off: - mutex_unlock(&dev->input_lock); - return ret; -} - -static int ov5693_g_frame_interval(struct v4l2_subdev *sd, - struct v4l2_subdev_frame_interval *interval) -{ - struct ov5693_device *dev = to_ov5693_sensor(sd); - - interval->interval.numerator = 1; - interval->interval.denominator = ov5693_res[dev->fmt_idx].fps; - - return 0; -} - -static int ov5693_enum_mbus_code(struct v4l2_subdev *sd, - struct v4l2_subdev_state *sd_state, - struct v4l2_subdev_mbus_code_enum *code) -{ - if (code->index >= MAX_FMTS) - return -EINVAL; - - code->code = MEDIA_BUS_FMT_SBGGR10_1X10; - return 0; -} - -static int ov5693_enum_frame_size(struct v4l2_subdev *sd, - struct v4l2_subdev_state *sd_state, - struct v4l2_subdev_frame_size_enum *fse) -{ - int index = fse->index; - - if (index >= N_RES) - return -EINVAL; - - fse->min_width = ov5693_res[index].width; - fse->min_height = ov5693_res[index].height; - fse->max_width = ov5693_res[index].width; - fse->max_height = ov5693_res[index].height; - - return 0; -} - -static const struct v4l2_subdev_video_ops ov5693_video_ops = { - .s_stream = ov5693_s_stream, - .g_frame_interval = ov5693_g_frame_interval, -}; - -static const struct v4l2_subdev_core_ops ov5693_core_ops = { - .s_power = ov5693_s_power, - .ioctl = ov5693_ioctl, -}; - -static const struct v4l2_subdev_pad_ops ov5693_pad_ops = { - .enum_mbus_code = ov5693_enum_mbus_code, - .enum_frame_size = ov5693_enum_frame_size, - .get_fmt = ov5693_get_fmt, - .set_fmt = ov5693_set_fmt, -}; - -static const struct v4l2_subdev_ops ov5693_ops = { - .core = &ov5693_core_ops, - .video = &ov5693_video_ops, - .pad = &ov5693_pad_ops, -}; - -static void ov5693_remove(struct i2c_client *client) -{ - struct v4l2_subdev *sd = i2c_get_clientdata(client); - struct ov5693_device *dev = to_ov5693_sensor(sd); - - dev_dbg(&client->dev, "ov5693_remove...\n"); - - dev->platform_data->csi_cfg(sd, 0); - - v4l2_device_unregister_subdev(sd); - - atomisp_gmin_remove_subdev(sd); - - media_entity_cleanup(&dev->sd.entity); - v4l2_ctrl_handler_free(&dev->ctrl_handler); - kfree(dev); -} - -static int ov5693_probe(struct i2c_client *client) -{ - struct ov5693_device *dev; - int i2c; - int ret; - void *pdata; - unsigned int i; - - /* - * Firmware workaround: Some modules use a "secondary default" - * address of 0x10 which doesn't appear on schematics, and - * some BIOS versions haven't gotten the memo. Work around - * via config. - */ - i2c = gmin_get_var_int(&client->dev, false, "I2CAddr", -1); - if (i2c != -1) { - dev_info(&client->dev, - "Overriding firmware-provided I2C address (0x%x) with 0x%x\n", - client->addr, i2c); - client->addr = i2c; - } - - dev = kzalloc(sizeof(*dev), GFP_KERNEL); - if (!dev) - return -ENOMEM; - - mutex_init(&dev->input_lock); - - dev->fmt_idx = 0; - v4l2_i2c_subdev_init(&dev->sd, client, &ov5693_ops); - - pdata = gmin_camera_platform_data(&dev->sd, - ATOMISP_INPUT_FORMAT_RAW_10, - atomisp_bayer_order_bggr); - if (!pdata) { - ret = -EINVAL; - goto out_free; - } - - ret = ov5693_s_config(&dev->sd, client->irq, pdata); - if (ret) - goto out_free; - - ret = atomisp_register_i2c_module(&dev->sd, pdata, RAW_CAMERA); - if (ret) - goto out_free; - - dev->sd.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE; - dev->pad.flags = MEDIA_PAD_FL_SOURCE; - dev->format.code = MEDIA_BUS_FMT_SBGGR10_1X10; - dev->sd.entity.function = MEDIA_ENT_F_CAM_SENSOR; - ret = - v4l2_ctrl_handler_init(&dev->ctrl_handler, - ARRAY_SIZE(ov5693_controls)); - if (ret) { - ov5693_remove(client); - return ret; - } - - for (i = 0; i < ARRAY_SIZE(ov5693_controls); i++) - v4l2_ctrl_new_custom(&dev->ctrl_handler, &ov5693_controls[i], - NULL); - - if (dev->ctrl_handler.error) { - ov5693_remove(client); - return dev->ctrl_handler.error; - } - - /* Use same lock for controls as for everything else. */ - dev->ctrl_handler.lock = &dev->input_lock; - dev->sd.ctrl_handler = &dev->ctrl_handler; - - ret = media_entity_pads_init(&dev->sd.entity, 1, &dev->pad); - if (ret) - ov5693_remove(client); - - return ret; -out_free: - v4l2_device_unregister_subdev(&dev->sd); - kfree(dev); - return ret; -} - -static const struct acpi_device_id ov5693_acpi_match[] = { - {"INT33BE"}, - {}, -}; -MODULE_DEVICE_TABLE(acpi, ov5693_acpi_match); - -static struct i2c_driver ov5693_driver = { - .driver = { - .name = "ov5693", - .acpi_match_table = ov5693_acpi_match, - }, - .probe = ov5693_probe, - .remove = ov5693_remove, -}; -module_i2c_driver(ov5693_driver); - -MODULE_DESCRIPTION("A low-level driver for OmniVision 5693 sensors"); -MODULE_LICENSE("GPL"); diff --git a/drivers/staging/media/atomisp/i2c/ov5693/ov5693.h b/drivers/staging/media/atomisp/i2c/ov5693/ov5693.h deleted file mode 100644 index 5e17eaf8fd6e..000000000000 --- a/drivers/staging/media/atomisp/i2c/ov5693/ov5693.h +++ /dev/null @@ -1,1331 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ -/* - * Support for OmniVision OV5693 5M camera sensor. - * - * Copyright (c) 2013 Intel Corporation. All Rights Reserved. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License version - * 2 as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * - */ - -#ifndef __OV5693_H__ -#define __OV5693_H__ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "../../include/linux/atomisp_platform.h" - -/* - * FIXME: non-preview resolutions are currently broken - */ -#define ENABLE_NON_PREVIEW 0 - -#define OV5693_POWER_UP_RETRY_NUM 5 - -/* Defines for register writes and register array processing */ -#define I2C_MSG_LENGTH 0x2 -#define I2C_RETRY_COUNT 5 - -#define OV5693_FOCAL_LENGTH_NUM 334 /*3.34mm*/ -#define OV5693_FOCAL_LENGTH_DEM 100 -#define OV5693_F_NUMBER_DEFAULT_NUM 24 -#define OV5693_F_NUMBER_DEM 10 - -#define MAX_FMTS 1 - -/* sensor_mode_data read_mode adaptation */ -#define OV5693_READ_MODE_BINNING_ON 0x0400 -#define OV5693_READ_MODE_BINNING_OFF 0x00 -#define OV5693_INTEGRATION_TIME_MARGIN 8 - -#define OV5693_MAX_EXPOSURE_VALUE 0xFFF1 -#define OV5693_MAX_GAIN_VALUE 0xFF - -/* - * focal length bits definition: - * bits 31-16: numerator, bits 15-0: denominator - */ -#define OV5693_FOCAL_LENGTH_DEFAULT 0x1B70064 - -/* - * current f-number bits definition: - * bits 31-16: numerator, bits 15-0: denominator - */ -#define OV5693_F_NUMBER_DEFAULT 0x18000a - -/* - * f-number range bits definition: - * bits 31-24: max f-number numerator - * bits 23-16: max f-number denominator - * bits 15-8: min f-number numerator - * bits 7-0: min f-number denominator - */ -#define OV5693_F_NUMBER_RANGE 0x180a180a -#define OV5693_ID 0x5690 - -#define OV5693_FINE_INTG_TIME_MIN 0 -#define OV5693_FINE_INTG_TIME_MAX_MARGIN 0 -#define OV5693_COARSE_INTG_TIME_MIN 1 -#define OV5693_COARSE_INTG_TIME_MAX_MARGIN 6 - -#define OV5693_BIN_FACTOR_MAX 4 -/* - * OV5693 System control registers - */ -#define OV5693_SW_SLEEP 0x0100 -#define OV5693_SW_RESET 0x0103 -#define OV5693_SW_STREAM 0x0100 - -#define OV5693_SC_CMMN_CHIP_ID_H 0x300A -#define OV5693_SC_CMMN_CHIP_ID_L 0x300B -#define OV5693_SC_CMMN_SCCB_ID 0x300C -#define OV5693_SC_CMMN_SUB_ID 0x302A /* process, version*/ -/*Bit[7:4] Group control, Bit[3:0] Group ID*/ -#define OV5693_GROUP_ACCESS 0x3208 -/* -*Bit[3:0] Bit[19:16] of exposure, -*remaining 16 bits lies in Reg0x3501&Reg0x3502 -*/ -#define OV5693_EXPOSURE_H 0x3500 -#define OV5693_EXPOSURE_M 0x3501 -#define OV5693_EXPOSURE_L 0x3502 -/*Bit[1:0] means Bit[9:8] of gain*/ -#define OV5693_AGC_H 0x350A -#define OV5693_AGC_L 0x350B /*Bit[7:0] of gain*/ - -#define OV5693_HORIZONTAL_START_H 0x3800 /*Bit[11:8]*/ -#define OV5693_HORIZONTAL_START_L 0x3801 /*Bit[7:0]*/ -#define OV5693_VERTICAL_START_H 0x3802 /*Bit[11:8]*/ -#define OV5693_VERTICAL_START_L 0x3803 /*Bit[7:0]*/ -#define OV5693_HORIZONTAL_END_H 0x3804 /*Bit[11:8]*/ -#define OV5693_HORIZONTAL_END_L 0x3805 /*Bit[7:0]*/ -#define OV5693_VERTICAL_END_H 0x3806 /*Bit[11:8]*/ -#define OV5693_VERTICAL_END_L 0x3807 /*Bit[7:0]*/ -#define OV5693_HORIZONTAL_OUTPUT_SIZE_H 0x3808 /*Bit[3:0]*/ -#define OV5693_HORIZONTAL_OUTPUT_SIZE_L 0x3809 /*Bit[7:0]*/ -#define OV5693_VERTICAL_OUTPUT_SIZE_H 0x380a /*Bit[3:0]*/ -#define OV5693_VERTICAL_OUTPUT_SIZE_L 0x380b /*Bit[7:0]*/ -/*High 8-bit, and low 8-bit HTS address is 0x380d*/ -#define OV5693_TIMING_HTS_H 0x380C -/*High 8-bit, and low 8-bit HTS address is 0x380d*/ -#define OV5693_TIMING_HTS_L 0x380D -/*High 8-bit, and low 8-bit HTS address is 0x380f*/ -#define OV5693_TIMING_VTS_H 0x380e -/*High 8-bit, and low 8-bit HTS address is 0x380f*/ -#define OV5693_TIMING_VTS_L 0x380f - -#define OV5693_MWB_RED_GAIN_H 0x3400 -#define OV5693_MWB_GREEN_GAIN_H 0x3402 -#define OV5693_MWB_BLUE_GAIN_H 0x3404 -#define OV5693_MWB_GAIN_MAX 0x0fff - -#define OV5693_START_STREAMING 0x01 -#define OV5693_STOP_STREAMING 0x00 - -#define VCM_ADDR 0x0c -#define VCM_CODE_MSB 0x04 - -#define OV5693_INVALID_CONFIG 0xffffffff - -#define OV5693_VCM_SLEW_STEP 0x30F0 -#define OV5693_VCM_SLEW_STEP_MAX 0x7 -#define OV5693_VCM_SLEW_STEP_MASK 0x7 -#define OV5693_VCM_CODE 0x30F2 -#define OV5693_VCM_SLEW_TIME 0x30F4 -#define OV5693_VCM_SLEW_TIME_MAX 0xffff -#define OV5693_VCM_ENABLE 0x8000 - -#define OV5693_VCM_MAX_FOCUS_NEG -1023 -#define OV5693_VCM_MAX_FOCUS_POS 1023 - -#define DLC_ENABLE 1 -#define DLC_DISABLE 0 -#define VCM_PROTECTION_OFF 0xeca3 -#define VCM_PROTECTION_ON 0xdc51 -#define VCM_DEFAULT_S 0x0 -#define vcm_step_s(a) (u8)(a & 0xf) -#define vcm_step_mclk(a) (u8)((a >> 4) & 0x3) -#define vcm_dlc_mclk(dlc, mclk) (u16)((dlc << 3) | mclk | 0xa104) -#define vcm_tsrc(tsrc) (u16)(tsrc << 3 | 0xf200) -#define vcm_val(data, s) (u16)(data << 4 | s) -#define DIRECT_VCM vcm_dlc_mclk(0, 0) - -/* Defines for OTP Data Registers */ -#define OV5693_FRAME_OFF_NUM 0x4202 -#define OV5693_OTP_BYTE_MAX 32 //change to 32 as needed by otpdata -#define OV5693_OTP_SHORT_MAX 16 -#define OV5693_OTP_START_ADDR 0x3D00 -#define OV5693_OTP_END_ADDR 0x3D0F -#define OV5693_OTP_DATA_SIZE 320 -#define OV5693_OTP_PROGRAM_REG 0x3D80 -#define OV5693_OTP_READ_REG 0x3D81 // 1:Enable 0:disable -#define OV5693_OTP_BANK_REG 0x3D84 //otp bank and mode -#define OV5693_OTP_READY_REG_DONE 1 -#define OV5693_OTP_BANK_MAX 28 -#define OV5693_OTP_BANK_SIZE 16 //16 bytes per bank -#define OV5693_OTP_READ_ONETIME 16 -#define OV5693_OTP_MODE_READ 1 - -struct regval_list { - u16 reg_num; - u8 value; -}; - -struct ov5693_resolution { - u8 *desc; - const struct ov5693_reg *regs; - int res; - int width; - int height; - int fps; - int pix_clk_freq; - u16 pixels_per_line; - u16 lines_per_frame; - bool used; -}; - -struct ov5693_format { - u8 *desc; - u32 pixelformat; - struct ov5693_reg *regs; -}; - -enum vcm_type { - VCM_UNKNOWN, - VCM_AD5823, - VCM_DW9714, -}; - -/* - * ov5693 device structure. - */ -struct ov5693_device { - struct v4l2_subdev sd; - struct media_pad pad; - struct v4l2_mbus_framefmt format; - struct mutex input_lock; - struct v4l2_ctrl_handler ctrl_handler; - - struct camera_sensor_platform_data *platform_data; - ktime_t timestamp_t_focus_abs; - int fmt_idx; - int run_mode; - int otp_size; - u8 *otp_data; - u32 focus; - s16 number_of_steps; - u8 res; - u8 type; - bool vcm_update; - enum vcm_type vcm; -}; - -enum ov5693_tok_type { - OV5693_8BIT = 0x0001, - OV5693_16BIT = 0x0002, - OV5693_32BIT = 0x0004, - OV5693_TOK_TERM = 0xf000, /* terminating token for reg list */ - OV5693_TOK_DELAY = 0xfe00, /* delay token for reg list */ - OV5693_TOK_MASK = 0xfff0 -}; - -/** - * struct ov5693_reg - MI sensor register format - * @type: type of the register - * @reg: 16-bit offset to register - * @val: 8/16/32-bit register value - * - * Define a structure for sensor register initialization values - */ -struct ov5693_reg { - enum ov5693_tok_type type; - u16 reg; - u32 val; /* @set value for read/mod/write, @mask */ -}; - -#define to_ov5693_sensor(x) container_of(x, struct ov5693_device, sd) - -#define OV5693_MAX_WRITE_BUF_SIZE 30 - -struct ov5693_write_buffer { - u16 addr; - u8 data[OV5693_MAX_WRITE_BUF_SIZE]; -}; - -struct ov5693_write_ctrl { - int index; - struct ov5693_write_buffer buffer; -}; - -static struct ov5693_reg const ov5693_global_setting[] = { - {OV5693_8BIT, 0x0103, 0x01}, - {OV5693_8BIT, 0x3001, 0x0a}, - {OV5693_8BIT, 0x3002, 0x80}, - {OV5693_8BIT, 0x3006, 0x00}, - {OV5693_8BIT, 0x3011, 0x21}, - {OV5693_8BIT, 0x3012, 0x09}, - {OV5693_8BIT, 0x3013, 0x10}, - {OV5693_8BIT, 0x3014, 0x00}, - {OV5693_8BIT, 0x3015, 0x08}, - {OV5693_8BIT, 0x3016, 0xf0}, - {OV5693_8BIT, 0x3017, 0xf0}, - {OV5693_8BIT, 0x3018, 0xf0}, - {OV5693_8BIT, 0x301b, 0xb4}, - {OV5693_8BIT, 0x301d, 0x02}, - {OV5693_8BIT, 0x3021, 0x00}, - {OV5693_8BIT, 0x3022, 0x01}, - {OV5693_8BIT, 0x3028, 0x44}, - {OV5693_8BIT, 0x3098, 0x02}, - {OV5693_8BIT, 0x3099, 0x19}, - {OV5693_8BIT, 0x309a, 0x02}, - {OV5693_8BIT, 0x309b, 0x01}, - {OV5693_8BIT, 0x309c, 0x00}, - {OV5693_8BIT, 0x30a0, 0xd2}, - {OV5693_8BIT, 0x30a2, 0x01}, - {OV5693_8BIT, 0x30b2, 0x00}, - {OV5693_8BIT, 0x30b3, 0x7d}, - {OV5693_8BIT, 0x30b4, 0x03}, - {OV5693_8BIT, 0x30b5, 0x04}, - {OV5693_8BIT, 0x30b6, 0x01}, - {OV5693_8BIT, 0x3104, 0x21}, - {OV5693_8BIT, 0x3106, 0x00}, - {OV5693_8BIT, 0x3400, 0x04}, - {OV5693_8BIT, 0x3401, 0x00}, - {OV5693_8BIT, 0x3402, 0x04}, - {OV5693_8BIT, 0x3403, 0x00}, - {OV5693_8BIT, 0x3404, 0x04}, - {OV5693_8BIT, 0x3405, 0x00}, - {OV5693_8BIT, 0x3406, 0x01}, - {OV5693_8BIT, 0x3500, 0x00}, - {OV5693_8BIT, 0x3503, 0x07}, - {OV5693_8BIT, 0x3504, 0x00}, - {OV5693_8BIT, 0x3505, 0x00}, - {OV5693_8BIT, 0x3506, 0x00}, - {OV5693_8BIT, 0x3507, 0x02}, - {OV5693_8BIT, 0x3508, 0x00}, - {OV5693_8BIT, 0x3509, 0x10}, - {OV5693_8BIT, 0x350a, 0x00}, - {OV5693_8BIT, 0x350b, 0x40}, - {OV5693_8BIT, 0x3601, 0x0a}, - {OV5693_8BIT, 0x3602, 0x38}, - {OV5693_8BIT, 0x3612, 0x80}, - {OV5693_8BIT, 0x3620, 0x54}, - {OV5693_8BIT, 0x3621, 0xc7}, - {OV5693_8BIT, 0x3622, 0x0f}, - {OV5693_8BIT, 0x3625, 0x10}, - {OV5693_8BIT, 0x3630, 0x55}, - {OV5693_8BIT, 0x3631, 0xf4}, - {OV5693_8BIT, 0x3632, 0x00}, - {OV5693_8BIT, 0x3633, 0x34}, - {OV5693_8BIT, 0x3634, 0x02}, - {OV5693_8BIT, 0x364d, 0x0d}, - {OV5693_8BIT, 0x364f, 0xdd}, - {OV5693_8BIT, 0x3660, 0x04}, - {OV5693_8BIT, 0x3662, 0x10}, - {OV5693_8BIT, 0x3663, 0xf1}, - {OV5693_8BIT, 0x3665, 0x00}, - {OV5693_8BIT, 0x3666, 0x20}, - {OV5693_8BIT, 0x3667, 0x00}, - {OV5693_8BIT, 0x366a, 0x80}, - {OV5693_8BIT, 0x3680, 0xe0}, - {OV5693_8BIT, 0x3681, 0x00}, - {OV5693_8BIT, 0x3700, 0x42}, - {OV5693_8BIT, 0x3701, 0x14}, - {OV5693_8BIT, 0x3702, 0xa0}, - {OV5693_8BIT, 0x3703, 0xd8}, - {OV5693_8BIT, 0x3704, 0x78}, - {OV5693_8BIT, 0x3705, 0x02}, - {OV5693_8BIT, 0x370a, 0x00}, - {OV5693_8BIT, 0x370b, 0x20}, - {OV5693_8BIT, 0x370c, 0x0c}, - {OV5693_8BIT, 0x370d, 0x11}, - {OV5693_8BIT, 0x370e, 0x00}, - {OV5693_8BIT, 0x370f, 0x40}, - {OV5693_8BIT, 0x3710, 0x00}, - {OV5693_8BIT, 0x371a, 0x1c}, - {OV5693_8BIT, 0x371b, 0x05}, - {OV5693_8BIT, 0x371c, 0x01}, - {OV5693_8BIT, 0x371e, 0xa1}, - {OV5693_8BIT, 0x371f, 0x0c}, - {OV5693_8BIT, 0x3721, 0x00}, - {OV5693_8BIT, 0x3724, 0x10}, - {OV5693_8BIT, 0x3726, 0x00}, - {OV5693_8BIT, 0x372a, 0x01}, - {OV5693_8BIT, 0x3730, 0x10}, - {OV5693_8BIT, 0x3738, 0x22}, - {OV5693_8BIT, 0x3739, 0xe5}, - {OV5693_8BIT, 0x373a, 0x50}, - {OV5693_8BIT, 0x373b, 0x02}, - {OV5693_8BIT, 0x373c, 0x41}, - {OV5693_8BIT, 0x373f, 0x02}, - {OV5693_8BIT, 0x3740, 0x42}, - {OV5693_8BIT, 0x3741, 0x02}, - {OV5693_8BIT, 0x3742, 0x18}, - {OV5693_8BIT, 0x3743, 0x01}, - {OV5693_8BIT, 0x3744, 0x02}, - {OV5693_8BIT, 0x3747, 0x10}, - {OV5693_8BIT, 0x374c, 0x04}, - {OV5693_8BIT, 0x3751, 0xf0}, - {OV5693_8BIT, 0x3752, 0x00}, - {OV5693_8BIT, 0x3753, 0x00}, - {OV5693_8BIT, 0x3754, 0xc0}, - {OV5693_8BIT, 0x3755, 0x00}, - {OV5693_8BIT, 0x3756, 0x1a}, - {OV5693_8BIT, 0x3758, 0x00}, - {OV5693_8BIT, 0x3759, 0x0f}, - {OV5693_8BIT, 0x376b, 0x44}, - {OV5693_8BIT, 0x375c, 0x04}, - {OV5693_8BIT, 0x3774, 0x10}, - {OV5693_8BIT, 0x3776, 0x00}, - {OV5693_8BIT, 0x377f, 0x08}, - {OV5693_8BIT, 0x3780, 0x22}, - {OV5693_8BIT, 0x3781, 0x0c}, - {OV5693_8BIT, 0x3784, 0x2c}, - {OV5693_8BIT, 0x3785, 0x1e}, - {OV5693_8BIT, 0x378f, 0xf5}, - {OV5693_8BIT, 0x3791, 0xb0}, - {OV5693_8BIT, 0x3795, 0x00}, - {OV5693_8BIT, 0x3796, 0x64}, - {OV5693_8BIT, 0x3797, 0x11}, - {OV5693_8BIT, 0x3798, 0x30}, - {OV5693_8BIT, 0x3799, 0x41}, - {OV5693_8BIT, 0x379a, 0x07}, - {OV5693_8BIT, 0x379b, 0xb0}, - {OV5693_8BIT, 0x379c, 0x0c}, - {OV5693_8BIT, 0x37c5, 0x00}, - {OV5693_8BIT, 0x37c6, 0x00}, - {OV5693_8BIT, 0x37c7, 0x00}, - {OV5693_8BIT, 0x37c9, 0x00}, - {OV5693_8BIT, 0x37ca, 0x00}, - {OV5693_8BIT, 0x37cb, 0x00}, - {OV5693_8BIT, 0x37de, 0x00}, - {OV5693_8BIT, 0x37df, 0x00}, - {OV5693_8BIT, 0x3800, 0x00}, - {OV5693_8BIT, 0x3801, 0x00}, - {OV5693_8BIT, 0x3802, 0x00}, - {OV5693_8BIT, 0x3804, 0x0a}, - {OV5693_8BIT, 0x3805, 0x3f}, - {OV5693_8BIT, 0x3810, 0x00}, - {OV5693_8BIT, 0x3812, 0x00}, - {OV5693_8BIT, 0x3823, 0x00}, - {OV5693_8BIT, 0x3824, 0x00}, - {OV5693_8BIT, 0x3825, 0x00}, - {OV5693_8BIT, 0x3826, 0x00}, - {OV5693_8BIT, 0x3827, 0x00}, - {OV5693_8BIT, 0x382a, 0x04}, - {OV5693_8BIT, 0x3a04, 0x06}, - {OV5693_8BIT, 0x3a05, 0x14}, - {OV5693_8BIT, 0x3a06, 0x00}, - {OV5693_8BIT, 0x3a07, 0xfe}, - {OV5693_8BIT, 0x3b00, 0x00}, - {OV5693_8BIT, 0x3b02, 0x00}, - {OV5693_8BIT, 0x3b03, 0x00}, - {OV5693_8BIT, 0x3b04, 0x00}, - {OV5693_8BIT, 0x3b05, 0x00}, - {OV5693_8BIT, 0x3e07, 0x20}, - {OV5693_8BIT, 0x4000, 0x08}, - {OV5693_8BIT, 0x4001, 0x04}, - {OV5693_8BIT, 0x4002, 0x45}, - {OV5693_8BIT, 0x4004, 0x08}, - {OV5693_8BIT, 0x4005, 0x18}, - {OV5693_8BIT, 0x4006, 0x20}, - {OV5693_8BIT, 0x4008, 0x24}, - {OV5693_8BIT, 0x4009, 0x10}, - {OV5693_8BIT, 0x400c, 0x00}, - {OV5693_8BIT, 0x400d, 0x00}, - {OV5693_8BIT, 0x4058, 0x00}, - {OV5693_8BIT, 0x404e, 0x37}, - {OV5693_8BIT, 0x404f, 0x8f}, - {OV5693_8BIT, 0x4058, 0x00}, - {OV5693_8BIT, 0x4101, 0xb2}, - {OV5693_8BIT, 0x4303, 0x00}, - {OV5693_8BIT, 0x4304, 0x08}, - {OV5693_8BIT, 0x4307, 0x31}, - {OV5693_8BIT, 0x4311, 0x04}, - {OV5693_8BIT, 0x4315, 0x01}, - {OV5693_8BIT, 0x4511, 0x05}, - {OV5693_8BIT, 0x4512, 0x01}, - {OV5693_8BIT, 0x4806, 0x00}, - {OV5693_8BIT, 0x4816, 0x52}, - {OV5693_8BIT, 0x481f, 0x30}, - {OV5693_8BIT, 0x4826, 0x2c}, - {OV5693_8BIT, 0x4831, 0x64}, - {OV5693_8BIT, 0x4d00, 0x04}, - {OV5693_8BIT, 0x4d01, 0x71}, - {OV5693_8BIT, 0x4d02, 0xfd}, - {OV5693_8BIT, 0x4d03, 0xf5}, - {OV5693_8BIT, 0x4d04, 0x0c}, - {OV5693_8BIT, 0x4d05, 0xcc}, - {OV5693_8BIT, 0x4837, 0x0a}, - {OV5693_8BIT, 0x5000, 0x06}, - {OV5693_8BIT, 0x5001, 0x01}, - {OV5693_8BIT, 0x5003, 0x20}, - {OV5693_8BIT, 0x5046, 0x0a}, - {OV5693_8BIT, 0x5013, 0x00}, - {OV5693_8BIT, 0x5046, 0x0a}, - {OV5693_8BIT, 0x5780, 0x1c}, - {OV5693_8BIT, 0x5786, 0x20}, - {OV5693_8BIT, 0x5787, 0x10}, - {OV5693_8BIT, 0x5788, 0x18}, - {OV5693_8BIT, 0x578a, 0x04}, - {OV5693_8BIT, 0x578b, 0x02}, - {OV5693_8BIT, 0x578c, 0x02}, - {OV5693_8BIT, 0x578e, 0x06}, - {OV5693_8BIT, 0x578f, 0x02}, - {OV5693_8BIT, 0x5790, 0x02}, - {OV5693_8BIT, 0x5791, 0xff}, - {OV5693_8BIT, 0x5842, 0x01}, - {OV5693_8BIT, 0x5843, 0x2b}, - {OV5693_8BIT, 0x5844, 0x01}, - {OV5693_8BIT, 0x5845, 0x92}, - {OV5693_8BIT, 0x5846, 0x01}, - {OV5693_8BIT, 0x5847, 0x8f}, - {OV5693_8BIT, 0x5848, 0x01}, - {OV5693_8BIT, 0x5849, 0x0c}, - {OV5693_8BIT, 0x5e00, 0x00}, - {OV5693_8BIT, 0x5e10, 0x0c}, - {OV5693_8BIT, 0x0100, 0x00}, - {OV5693_TOK_TERM, 0, 0} -}; - -#if ENABLE_NON_PREVIEW -/* - * 654x496 30fps 17ms VBlanking 2lane 10Bit (Scaling) - */ -static struct ov5693_reg const ov5693_654x496[] = { - {OV5693_8BIT, 0x3501, 0x3d}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe6}, - {OV5693_8BIT, 0x3709, 0xc7}, - {OV5693_8BIT, 0x3803, 0x00}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xa3}, - {OV5693_8BIT, 0x3808, 0x02}, - {OV5693_8BIT, 0x3809, 0x90}, - {OV5693_8BIT, 0x380a, 0x01}, - {OV5693_8BIT, 0x380b, 0xf0}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x08}, - {OV5693_8BIT, 0x3813, 0x02}, - {OV5693_8BIT, 0x3814, 0x31}, - {OV5693_8BIT, 0x3815, 0x31}, - {OV5693_8BIT, 0x3820, 0x04}, - {OV5693_8BIT, 0x3821, 0x1f}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -/* - * 1296x976 30fps 17ms VBlanking 2lane 10Bit (Scaling) -*DS from 2592x1952 -*/ -static struct ov5693_reg const ov5693_1296x976[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - - {OV5693_8BIT, 0x3800, 0x00}, - {OV5693_8BIT, 0x3801, 0x00}, - {OV5693_8BIT, 0x3802, 0x00}, - {OV5693_8BIT, 0x3803, 0x00}, - - {OV5693_8BIT, 0x3804, 0x0a}, - {OV5693_8BIT, 0x3805, 0x3f}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xA3}, - - {OV5693_8BIT, 0x3808, 0x05}, - {OV5693_8BIT, 0x3809, 0x10}, - {OV5693_8BIT, 0x380a, 0x03}, - {OV5693_8BIT, 0x380b, 0xD0}, - - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - - {OV5693_8BIT, 0x3810, 0x00}, - {OV5693_8BIT, 0x3811, 0x10}, - {OV5693_8BIT, 0x3812, 0x00}, - {OV5693_8BIT, 0x3813, 0x02}, - - {OV5693_8BIT, 0x3814, 0x11}, /*X subsample control*/ - {OV5693_8BIT, 0x3815, 0x11}, /*Y subsample control*/ - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x5041, 0x84}, /* scale is auto enabled */ - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} - -}; - -/* - * 336x256 30fps 17ms VBlanking 2lane 10Bit (Scaling) - DS from 2564x1956 - */ -static struct ov5693_reg const ov5693_336x256[] = { - {OV5693_8BIT, 0x3501, 0x3d}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe6}, - {OV5693_8BIT, 0x3709, 0xc7}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xa3}, - {OV5693_8BIT, 0x3808, 0x01}, - {OV5693_8BIT, 0x3809, 0x50}, - {OV5693_8BIT, 0x380a, 0x01}, - {OV5693_8BIT, 0x380b, 0x00}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x1E}, - {OV5693_8BIT, 0x3814, 0x31}, - {OV5693_8BIT, 0x3815, 0x31}, - {OV5693_8BIT, 0x3820, 0x04}, - {OV5693_8BIT, 0x3821, 0x1f}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -/* - * 336x256 30fps 17ms VBlanking 2lane 10Bit (Scaling) - DS from 2368x1956 - */ -static struct ov5693_reg const ov5693_368x304[] = { - {OV5693_8BIT, 0x3501, 0x3d}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe6}, - {OV5693_8BIT, 0x3709, 0xc7}, - {OV5693_8BIT, 0x3808, 0x01}, - {OV5693_8BIT, 0x3809, 0x70}, - {OV5693_8BIT, 0x380a, 0x01}, - {OV5693_8BIT, 0x380b, 0x30}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x80}, - {OV5693_8BIT, 0x3814, 0x31}, - {OV5693_8BIT, 0x3815, 0x31}, - {OV5693_8BIT, 0x3820, 0x04}, - {OV5693_8BIT, 0x3821, 0x1f}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -/* - * ov5693_192x160 30fps 17ms VBlanking 2lane 10Bit (Scaling) - DS from 2460x1956 - */ -static struct ov5693_reg const ov5693_192x160[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x80}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3804, 0x0a}, - {OV5693_8BIT, 0x3805, 0x3f}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xA3}, - {OV5693_8BIT, 0x3808, 0x00}, - {OV5693_8BIT, 0x3809, 0xC0}, - {OV5693_8BIT, 0x380a, 0x00}, - {OV5693_8BIT, 0x380b, 0xA0}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x40}, - {OV5693_8BIT, 0x3813, 0x00}, - {OV5693_8BIT, 0x3814, 0x31}, - {OV5693_8BIT, 0x3815, 0x31}, - {OV5693_8BIT, 0x3820, 0x04}, - {OV5693_8BIT, 0x3821, 0x1f}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -static struct ov5693_reg const ov5693_736x496[] = { - {OV5693_8BIT, 0x3501, 0x3d}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe6}, - {OV5693_8BIT, 0x3709, 0xc7}, - {OV5693_8BIT, 0x3803, 0x68}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0x3b}, - {OV5693_8BIT, 0x3808, 0x02}, - {OV5693_8BIT, 0x3809, 0xe0}, - {OV5693_8BIT, 0x380a, 0x01}, - {OV5693_8BIT, 0x380b, 0xf0}, - {OV5693_8BIT, 0x380c, 0x0a}, /*hts*/ - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, /*vts*/ - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x08}, - {OV5693_8BIT, 0x3813, 0x02}, - {OV5693_8BIT, 0x3814, 0x31}, - {OV5693_8BIT, 0x3815, 0x31}, - {OV5693_8BIT, 0x3820, 0x04}, - {OV5693_8BIT, 0x3821, 0x1f}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; -#endif - -/* -static struct ov5693_reg const ov5693_736x496[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe6}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3803, 0x00}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xa3}, - {OV5693_8BIT, 0x3808, 0x02}, - {OV5693_8BIT, 0x3809, 0xe0}, - {OV5693_8BIT, 0x380a, 0x01}, - {OV5693_8BIT, 0x380b, 0xf0}, - {OV5693_8BIT, 0x380c, 0x0d}, - {OV5693_8BIT, 0x380d, 0xb0}, - {OV5693_8BIT, 0x380e, 0x05}, - {OV5693_8BIT, 0x380f, 0xf2}, - {OV5693_8BIT, 0x3811, 0x08}, - {OV5693_8BIT, 0x3813, 0x02}, - {OV5693_8BIT, 0x3814, 0x31}, - {OV5693_8BIT, 0x3815, 0x31}, - {OV5693_8BIT, 0x3820, 0x01}, - {OV5693_8BIT, 0x3821, 0x1f}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; -*/ -/* - * 976x556 30fps 8.8ms VBlanking 2lane 10Bit (Scaling) - */ -#if ENABLE_NON_PREVIEW -static struct ov5693_reg const ov5693_976x556[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3803, 0xf0}, - {OV5693_8BIT, 0x3806, 0x06}, - {OV5693_8BIT, 0x3807, 0xa7}, - {OV5693_8BIT, 0x3808, 0x03}, - {OV5693_8BIT, 0x3809, 0xd0}, - {OV5693_8BIT, 0x380a, 0x02}, - {OV5693_8BIT, 0x380b, 0x2C}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x10}, - {OV5693_8BIT, 0x3813, 0x02}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -/*DS from 2624x1492*/ -static struct ov5693_reg const ov5693_1296x736[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - - {OV5693_8BIT, 0x3800, 0x00}, - {OV5693_8BIT, 0x3801, 0x00}, - {OV5693_8BIT, 0x3802, 0x00}, - {OV5693_8BIT, 0x3803, 0x00}, - - {OV5693_8BIT, 0x3804, 0x0a}, - {OV5693_8BIT, 0x3805, 0x3f}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xA3}, - - {OV5693_8BIT, 0x3808, 0x05}, - {OV5693_8BIT, 0x3809, 0x10}, - {OV5693_8BIT, 0x380a, 0x02}, - {OV5693_8BIT, 0x380b, 0xe0}, - - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - - {OV5693_8BIT, 0x3813, 0xE8}, - - {OV5693_8BIT, 0x3814, 0x11}, /*X subsample control*/ - {OV5693_8BIT, 0x3815, 0x11}, /*Y subsample control*/ - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x5041, 0x84}, /* scale is auto enabled */ - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -static struct ov5693_reg const ov5693_1636p_30fps[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3803, 0xf0}, - {OV5693_8BIT, 0x3806, 0x06}, - {OV5693_8BIT, 0x3807, 0xa7}, - {OV5693_8BIT, 0x3808, 0x06}, - {OV5693_8BIT, 0x3809, 0x64}, - {OV5693_8BIT, 0x380a, 0x04}, - {OV5693_8BIT, 0x380b, 0x48}, - {OV5693_8BIT, 0x380c, 0x0a}, /*hts*/ - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, /*vts*/ - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x02}, - {OV5693_8BIT, 0x3813, 0x02}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; -#endif - -static struct ov5693_reg const ov5693_1616x1216_30fps[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x80}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3800, 0x00}, /*{3800,3801} Array X start*/ - {OV5693_8BIT, 0x3801, 0x08}, /* 04 //{3800,3801} Array X start*/ - {OV5693_8BIT, 0x3802, 0x00}, /*{3802,3803} Array Y start*/ - {OV5693_8BIT, 0x3803, 0x04}, /* 00 //{3802,3803} Array Y start*/ - {OV5693_8BIT, 0x3804, 0x0a}, /*{3804,3805} Array X end*/ - {OV5693_8BIT, 0x3805, 0x37}, /* 3b //{3804,3805} Array X end*/ - {OV5693_8BIT, 0x3806, 0x07}, /*{3806,3807} Array Y end*/ - {OV5693_8BIT, 0x3807, 0x9f}, /* a3 //{3806,3807} Array Y end*/ - {OV5693_8BIT, 0x3808, 0x06}, /*{3808,3809} Final output H size*/ - {OV5693_8BIT, 0x3809, 0x50}, /*{3808,3809} Final output H size*/ - {OV5693_8BIT, 0x380a, 0x04}, /*{380a,380b} Final output V size*/ - {OV5693_8BIT, 0x380b, 0xc0}, /*{380a,380b} Final output V size*/ - {OV5693_8BIT, 0x380c, 0x0a}, /*{380c,380d} HTS*/ - {OV5693_8BIT, 0x380d, 0x80}, /*{380c,380d} HTS*/ - {OV5693_8BIT, 0x380e, 0x07}, /*{380e,380f} VTS*/ - {OV5693_8BIT, 0x380f, 0xc0}, /* bc //{380e,380f} VTS*/ - {OV5693_8BIT, 0x3810, 0x00}, /*{3810,3811} windowing X offset*/ - {OV5693_8BIT, 0x3811, 0x10}, /*{3810,3811} windowing X offset*/ - {OV5693_8BIT, 0x3812, 0x00}, /*{3812,3813} windowing Y offset*/ - {OV5693_8BIT, 0x3813, 0x06}, /*{3812,3813} windowing Y offset*/ - {OV5693_8BIT, 0x3814, 0x11}, /*X subsample control*/ - {OV5693_8BIT, 0x3815, 0x11}, /*Y subsample control*/ - {OV5693_8BIT, 0x3820, 0x00}, /*FLIP/Binning control*/ - {OV5693_8BIT, 0x3821, 0x1e}, /*MIRROR control*/ - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x5041, 0x84}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -/* - * 1940x1096 30fps 8.8ms VBlanking 2lane 10bit (Scaling) - */ -#if ENABLE_NON_PREVIEW -static struct ov5693_reg const ov5693_1940x1096[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3803, 0xf0}, - {OV5693_8BIT, 0x3806, 0x06}, - {OV5693_8BIT, 0x3807, 0xa7}, - {OV5693_8BIT, 0x3808, 0x07}, - {OV5693_8BIT, 0x3809, 0x94}, - {OV5693_8BIT, 0x380a, 0x04}, - {OV5693_8BIT, 0x380b, 0x48}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x02}, - {OV5693_8BIT, 0x3813, 0x02}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x80}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -static struct ov5693_reg const ov5693_2592x1456_30fps[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3800, 0x00}, - {OV5693_8BIT, 0x3801, 0x00}, - {OV5693_8BIT, 0x3802, 0x00}, - {OV5693_8BIT, 0x3803, 0xf0}, - {OV5693_8BIT, 0x3804, 0x0a}, - {OV5693_8BIT, 0x3805, 0x3f}, - {OV5693_8BIT, 0x3806, 0x06}, - {OV5693_8BIT, 0x3807, 0xa4}, - {OV5693_8BIT, 0x3808, 0x0a}, - {OV5693_8BIT, 0x3809, 0x20}, - {OV5693_8BIT, 0x380a, 0x05}, - {OV5693_8BIT, 0x380b, 0xb0}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x10}, - {OV5693_8BIT, 0x3813, 0x00}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_TOK_TERM, 0, 0} -}; -#endif - -static struct ov5693_reg const ov5693_2576x1456_30fps[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3800, 0x00}, - {OV5693_8BIT, 0x3801, 0x00}, - {OV5693_8BIT, 0x3802, 0x00}, - {OV5693_8BIT, 0x3803, 0xf0}, - {OV5693_8BIT, 0x3804, 0x0a}, - {OV5693_8BIT, 0x3805, 0x3f}, - {OV5693_8BIT, 0x3806, 0x06}, - {OV5693_8BIT, 0x3807, 0xa4}, - {OV5693_8BIT, 0x3808, 0x0a}, - {OV5693_8BIT, 0x3809, 0x10}, - {OV5693_8BIT, 0x380a, 0x05}, - {OV5693_8BIT, 0x380b, 0xb0}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x18}, - {OV5693_8BIT, 0x3813, 0x00}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_TOK_TERM, 0, 0} -}; - -/* - * 2592x1944 30fps 0.6ms VBlanking 2lane 10Bit - */ -#if ENABLE_NON_PREVIEW -static struct ov5693_reg const ov5693_2592x1944_30fps[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3803, 0x00}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xa3}, - {OV5693_8BIT, 0x3808, 0x0a}, - {OV5693_8BIT, 0x3809, 0x20}, - {OV5693_8BIT, 0x380a, 0x07}, - {OV5693_8BIT, 0x380b, 0x98}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x10}, - {OV5693_8BIT, 0x3813, 0x00}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; -#endif - -/* - * 11:9 Full FOV Output, expected FOV Res: 2346x1920 - * ISP Effect Res: 1408x1152 - * Sensor out: 1424x1168, DS From: 2380x1952 - * - * WA: Left Offset: 8, Hor scal: 64 - */ -#if ENABLE_NON_PREVIEW -static struct ov5693_reg const ov5693_1424x1168_30fps[] = { - {OV5693_8BIT, 0x3501, 0x3b}, /* long exposure[15:8] */ - {OV5693_8BIT, 0x3502, 0x80}, /* long exposure[7:0] */ - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3800, 0x00}, /* TIMING_X_ADDR_START */ - {OV5693_8BIT, 0x3801, 0x50}, /* 80 */ - {OV5693_8BIT, 0x3802, 0x00}, /* TIMING_Y_ADDR_START */ - {OV5693_8BIT, 0x3803, 0x02}, /* 2 */ - {OV5693_8BIT, 0x3804, 0x09}, /* TIMING_X_ADDR_END */ - {OV5693_8BIT, 0x3805, 0xdd}, /* 2525 */ - {OV5693_8BIT, 0x3806, 0x07}, /* TIMING_Y_ADDR_END */ - {OV5693_8BIT, 0x3807, 0xa1}, /* 1953 */ - {OV5693_8BIT, 0x3808, 0x05}, /* TIMING_X_OUTPUT_SIZE */ - {OV5693_8BIT, 0x3809, 0x90}, /* 1424 */ - {OV5693_8BIT, 0x380a, 0x04}, /* TIMING_Y_OUTPUT_SIZE */ - {OV5693_8BIT, 0x380b, 0x90}, /* 1168 */ - {OV5693_8BIT, 0x380c, 0x0a}, /* TIMING_HTS */ - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, /* TIMING_VTS */ - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3810, 0x00}, /* TIMING_ISP_X_WIN */ - {OV5693_8BIT, 0x3811, 0x02}, /* 2 */ - {OV5693_8BIT, 0x3812, 0x00}, /* TIMING_ISP_Y_WIN */ - {OV5693_8BIT, 0x3813, 0x00}, /* 0 */ - {OV5693_8BIT, 0x3814, 0x11}, /* TIME_X_INC */ - {OV5693_8BIT, 0x3815, 0x11}, /* TIME_Y_INC */ - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x5041, 0x84}, /* scale is auto enabled */ - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; -#endif - -/* - * 3:2 Full FOV Output, expected FOV Res: 2560x1706 - * ISP Effect Res: 720x480 - * Sensor out: 736x496, DS From 2616x1764 - */ -static struct ov5693_reg const ov5693_736x496_30fps[] = { - {OV5693_8BIT, 0x3501, 0x3b}, /* long exposure[15:8] */ - {OV5693_8BIT, 0x3502, 0x80}, /* long exposure[7:0] */ - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3800, 0x00}, /* TIMING_X_ADDR_START */ - {OV5693_8BIT, 0x3801, 0x02}, /* 2 */ - {OV5693_8BIT, 0x3802, 0x00}, /* TIMING_Y_ADDR_START */ - {OV5693_8BIT, 0x3803, 0x62}, /* 98 */ - {OV5693_8BIT, 0x3804, 0x0a}, /* TIMING_X_ADDR_END */ - {OV5693_8BIT, 0x3805, 0x3b}, /* 2619 */ - {OV5693_8BIT, 0x3806, 0x07}, /* TIMING_Y_ADDR_END */ - {OV5693_8BIT, 0x3807, 0x43}, /* 1859 */ - {OV5693_8BIT, 0x3808, 0x02}, /* TIMING_X_OUTPUT_SIZE */ - {OV5693_8BIT, 0x3809, 0xe0}, /* 736 */ - {OV5693_8BIT, 0x380a, 0x01}, /* TIMING_Y_OUTPUT_SIZE */ - {OV5693_8BIT, 0x380b, 0xf0}, /* 496 */ - {OV5693_8BIT, 0x380c, 0x0a}, /* TIMING_HTS */ - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, /* TIMING_VTS */ - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3810, 0x00}, /* TIMING_ISP_X_WIN */ - {OV5693_8BIT, 0x3811, 0x02}, /* 2 */ - {OV5693_8BIT, 0x3812, 0x00}, /* TIMING_ISP_Y_WIN */ - {OV5693_8BIT, 0x3813, 0x00}, /* 0 */ - {OV5693_8BIT, 0x3814, 0x11}, /* TIME_X_INC */ - {OV5693_8BIT, 0x3815, 0x11}, /* TIME_Y_INC */ - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x5041, 0x84}, /* scale is auto enabled */ - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -static struct ov5693_reg const ov5693_2576x1936_30fps[] = { - {OV5693_8BIT, 0x3501, 0x7b}, - {OV5693_8BIT, 0x3502, 0x00}, - {OV5693_8BIT, 0x3708, 0xe2}, - {OV5693_8BIT, 0x3709, 0xc3}, - {OV5693_8BIT, 0x3803, 0x00}, - {OV5693_8BIT, 0x3806, 0x07}, - {OV5693_8BIT, 0x3807, 0xa3}, - {OV5693_8BIT, 0x3808, 0x0a}, - {OV5693_8BIT, 0x3809, 0x10}, - {OV5693_8BIT, 0x380a, 0x07}, - {OV5693_8BIT, 0x380b, 0x90}, - {OV5693_8BIT, 0x380c, 0x0a}, - {OV5693_8BIT, 0x380d, 0x80}, - {OV5693_8BIT, 0x380e, 0x07}, - {OV5693_8BIT, 0x380f, 0xc0}, - {OV5693_8BIT, 0x3811, 0x18}, - {OV5693_8BIT, 0x3813, 0x00}, - {OV5693_8BIT, 0x3814, 0x11}, - {OV5693_8BIT, 0x3815, 0x11}, - {OV5693_8BIT, 0x3820, 0x00}, - {OV5693_8BIT, 0x3821, 0x1e}, - {OV5693_8BIT, 0x5002, 0x00}, - {OV5693_8BIT, 0x0100, 0x01}, - {OV5693_TOK_TERM, 0, 0} -}; - -static struct ov5693_resolution ov5693_res_preview[] = { - { - .desc = "ov5693_736x496_30fps", - .width = 736, - .height = 496, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_736x496_30fps, - }, - { - .desc = "ov5693_1616x1216_30fps", - .width = 1616, - .height = 1216, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1616x1216_30fps, - }, - { - .desc = "ov5693_5M_30fps", - .width = 2576, - .height = 1456, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_2576x1456_30fps, - }, - { - .desc = "ov5693_5M_30fps", - .width = 2576, - .height = 1936, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_2576x1936_30fps, - }, -}; - -#define N_RES_PREVIEW (ARRAY_SIZE(ov5693_res_preview)) - -/* - * Disable non-preview configurations until the configuration selection is - * improved. - */ -#if ENABLE_NON_PREVIEW -struct ov5693_resolution ov5693_res_still[] = { - { - .desc = "ov5693_736x496_30fps", - .width = 736, - .height = 496, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_736x496_30fps, - }, - { - .desc = "ov5693_1424x1168_30fps", - .width = 1424, - .height = 1168, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1424x1168_30fps, - }, - { - .desc = "ov5693_1616x1216_30fps", - .width = 1616, - .height = 1216, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1616x1216_30fps, - }, - { - .desc = "ov5693_5M_30fps", - .width = 2592, - .height = 1456, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_2592x1456_30fps, - }, - { - .desc = "ov5693_5M_30fps", - .width = 2592, - .height = 1944, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_2592x1944_30fps, - }, -}; - -#define N_RES_STILL (ARRAY_SIZE(ov5693_res_still)) - -struct ov5693_resolution ov5693_res_video[] = { - { - .desc = "ov5693_736x496_30fps", - .width = 736, - .height = 496, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_736x496, - }, - { - .desc = "ov5693_336x256_30fps", - .width = 336, - .height = 256, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_336x256, - }, - { - .desc = "ov5693_368x304_30fps", - .width = 368, - .height = 304, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_368x304, - }, - { - .desc = "ov5693_192x160_30fps", - .width = 192, - .height = 160, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_192x160, - }, - { - .desc = "ov5693_1296x736_30fps", - .width = 1296, - .height = 736, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1296x736, - }, - { - .desc = "ov5693_1296x976_30fps", - .width = 1296, - .height = 976, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1296x976, - }, - { - .desc = "ov5693_1636P_30fps", - .width = 1636, - .height = 1096, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1636p_30fps, - }, - { - .desc = "ov5693_1080P_30fps", - .width = 1940, - .height = 1096, - .fps = 30, - .pix_clk_freq = 160, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_1940x1096, - }, - { - .desc = "ov5693_5M_30fps", - .width = 2592, - .height = 1456, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_2592x1456_30fps, - }, - { - .desc = "ov5693_5M_30fps", - .width = 2592, - .height = 1944, - .pix_clk_freq = 160, - .fps = 30, - .used = 0, - .pixels_per_line = 2688, - .lines_per_frame = 1984, - .regs = ov5693_2592x1944_30fps, - }, -}; - -#define N_RES_VIDEO (ARRAY_SIZE(ov5693_res_video)) -#endif - -static struct ov5693_resolution *ov5693_res = ov5693_res_preview; -static unsigned long N_RES = N_RES_PREVIEW; -#endif