From nobody Mon Feb 9 21:00:32 2026 Received: from PNYPR01CU001.outbound.protection.outlook.com (mail-centralindiaazon11020102.outbound.protection.outlook.com [52.101.225.102]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 98B541E492D; Wed, 31 Dec 2025 07:07:33 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.225.102 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1767164855; cv=fail; b=J81WaAl3HpvWidVb56yIO2UObhETDXOfH67HQ4XhDMDsYVn+OP8ndtypl0kh+BsUSLWxlXTBjkyiOhv0w6cN6LJQWKhhUPCOYk7LvU0n9UNzSX9qNbL+6YC5AIolmzslcpcf0GVfM3ov3gTd7PrLEjJUzuq8qbaarc2uBhs0VhI= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1767164855; c=relaxed/simple; bh=47SSyVudXDRrhJNX/vzDB1u23YTxGvliOMofzZQP9zY=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: Content-Type:MIME-Version; b=YUxi9vGABBAJYVZwWhfX5FNjDr8AQyOWYtX3e5uDVPyY7+T/RxKlVWNkcrmQR7m9z5cx7Rc7Oq7zGxRVb6WvUP+zh7j/ezFBms8BpzosqI5QetWQ5EPbOKkmRhgs3TKXW7P1CAC9CKjIRBxneuY4yyrdnybIiAFey1dyahXRKL0= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=siliconsignals.io; spf=pass smtp.mailfrom=siliconsignals.io; dkim=pass (2048-bit key) header.d=siliconsignals.io header.i=@siliconsignals.io header.b=MpNN+m1p; arc=fail smtp.client-ip=52.101.225.102 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=siliconsignals.io Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=siliconsignals.io Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=siliconsignals.io header.i=@siliconsignals.io header.b="MpNN+m1p" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=g/LzFeH/crPkehhvan4H7XLq6V65ahXlQMbmjMgJJR9qIzNgpcjLxyIq6F5DK9Z/Wg7jZuL0dqDRpOtOh/fklq43tCwHty2jsjaWaADnu+dn5dPUGHYCoKcyWOEK49SWFZSqBg3fcD16QS5Hb1AT3jDY1UvpuFcDJTSW3xy+X4en8Si7UHn4fkLp04ksFqEI3qXQ8oVSGx9y10S8obTI0BvTVpXUr8Bdq+pz5W6cn/AkvsN1l6AgeZozC9LOsEVaeTHhfxgaKKsgyHLOTV1SqjNRpeA8HtTtM7VGvmFvAe7eUQOvdyrYZJmi9DreJmJCO05HD2vXNfH3B5hdM2b6pA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector10001; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=nvDDL5PnNI7GJl/6ikk2eDmXVtp4qruiJvvL3iEuqx0=; b=n4jDUkmXvYmDTSmzFp//6m3ET+Ou0YRW1BvT1QBgGRS4sr78ds1eZoeP3M7RlkVreqAb4GgkIgGM0YjoYAIHTZy5jAqg0e3G5rPaYMsGBR78rDIjvo2vUkDbuz1mqRMY4HkJFbD+iBOUZ7G7XbXWpbZrz2J2BW+6dFU5UF9yBA3YcXXfg/5hkvqbR3CeOiG16Y7b+fcm3PGYvKsPtcKlN4n+8mTl/YMYZtuVzvjxggr26bmbU8rNpUahe3lmWjorbz42TxMOVtWLqFen36twhFJD1c5Bc9Ik7M0DCB1SwDZjqrhZhlF8oN1Fy4aYIXzybpub99zfrTZU5NxpYJv/mQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=siliconsignals.io; dmarc=pass action=none header.from=siliconsignals.io; dkim=pass header.d=siliconsignals.io; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=siliconsignals.io; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=nvDDL5PnNI7GJl/6ikk2eDmXVtp4qruiJvvL3iEuqx0=; b=MpNN+m1pB0a86gC+yCBmwSGBKiCDVhxkiEugxqPicSmi58UpSqgcCz7KavQA89HogwBAD02aYwRy+jR6FeSVNB3CwW1GzBblkJFhcCO+deefmdTDrxfykgMk4apPztEh3bcH5/JjZHXt7MxBJ7zzelOLMwg9gGsmXy+P8KsxHamm+vMDEUTBWWBzEdlW6vHOeP96IISVu7WaW+wDfYWYzfZbrc/p8jIYMoMBUlgcbauhEbT5hVPvg61L3hGjKKQ4mFGlSDKRTUR38enUE4hPVfytHxc6zfkcxTOPo4IkTz3UidUEppzElVcZAkdZkGRQ5YfM5J+yJ/t3F/S4UCG3Ag== Authentication-Results: dkim=none (message not signed) header.d=none;dmarc=none action=none header.from=siliconsignals.io; Received: from PN2P287MB2030.INDP287.PROD.OUTLOOK.COM (2603:1096:c01:1c9::8) by MAZP287MB0021.INDP287.PROD.OUTLOOK.COM (2603:1096:a01:40::6) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.9478.4; Wed, 31 Dec 2025 07:07:29 +0000 Received: from PN2P287MB2030.INDP287.PROD.OUTLOOK.COM ([fe80::85bb:6572:ae6c:5a15]) by PN2P287MB2030.INDP287.PROD.OUTLOOK.COM ([fe80::85bb:6572:ae6c:5a15%3]) with mapi id 15.20.9456.008; Wed, 31 Dec 2025 07:07:29 +0000 From: Himanshu Bhavani To: robh@kernel.org, krzk+dt@kernel.org, sakari.ailus@linux.intel.com Cc: Elgin Perumbilly , Himanshu Bhavani , Vladimir Zapolskiy , Krzysztof Kozlowski , Mauro Carvalho Chehab , Conor Dooley , Hans Verkuil , Hans de Goede , Mehdi Djait , =?UTF-8?q?Andr=C3=A9=20Apitzsch?= , Laurent Pinchart , Sylvain Petinot , Dongcheng Yan , Benjamin Mugnier , Hardevsinh Palaniya , Svyatoslav Ryhel , Jingjing Xiong , Heimir Thor Sverrisson , linux-media@vger.kernel.org, devicetree@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH v7 1/2] dt-bindings: media: i2c: Add os05b10 sensor Date: Wed, 31 Dec 2025 12:36:37 +0530 Message-Id: <20251231070645.16434-2-himanshu.bhavani@siliconsignals.io> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20251231070645.16434-1-himanshu.bhavani@siliconsignals.io> References: <20251231070645.16434-1-himanshu.bhavani@siliconsignals.io> Content-Transfer-Encoding: quoted-printable X-ClientProxiedBy: PN3PR01CA0125.INDPRD01.PROD.OUTLOOK.COM (2603:1096:c01:96::11) To PN2P287MB2030.INDP287.PROD.OUTLOOK.COM (2603:1096:c01:1c9::8) Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: PN2P287MB2030:EE_|MAZP287MB0021:EE_ X-MS-Office365-Filtering-Correlation-Id: 9fe4a346-860d-4d1e-298a-08de483b4293 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|376014|52116014|7416014|1800799024|366016|38350700014; X-Microsoft-Antispam-Message-Info: =?us-ascii?Q?xTeKehFy+tsFteuANvf2CGK4mjTAWxcfFZeDRGjmtzxdEAJwVkyLyG/QkyyU?= =?us-ascii?Q?SFoKKpB8MVccBt3GF4m9BZRhNbW9Dc+r0GUlGLhb1uM8/EsUq3M7b4ynr3eu?= =?us-ascii?Q?VzmnUSQ37RNZRvFcfOiZkNc0zFI2nhYB5VOW4nrFrRBpwAW7HyCZKLf2uodq?= =?us-ascii?Q?FgQhIF2KC8ePq9orT3GNuijelyGuo0I44di8GRmx312hKNLdoXhrPl4WloVE?= =?us-ascii?Q?33+3q22+QA3UfpldhIcsWA9/CaObMv2cQa79vCgpDV3eCykPqIYlRqxiTW+0?= =?us-ascii?Q?zc8ndOoinLPnsMCYh9HkNqy8U60/O0806Sr1c5VCm7swIFmD3XkpyF65O1CM?= =?us-ascii?Q?uHZdSRhQaX+h53MvXALJspWW6rOrWyyxgdOAp3IdL505xg2LbBBJk5DCK44J?= =?us-ascii?Q?eM10iSUVFsfwcwfBAkE7wDg2/IWa9KzuDcygrVWph2+T75NQJQ/upD63Cvpi?= =?us-ascii?Q?kVr8NBEr5UUcjWme+BQoYWwcx/sGFYfa/V0LPUGHYMLHGZy862o322okIc5n?= =?us-ascii?Q?XOQMxbX4F6xUGOtzSEKWFtbWRAW4v65wxXlywekrWsWu5dNf8LhbxmEsQGxa?= =?us-ascii?Q?uza0RsToOWKLFOJrl19dk+lIOhec8VcJ357AjG0tzsxa5r8JoMadOl1I3Dhi?= =?us-ascii?Q?NkPXuOHAZjmOGJQItKWd/Zpzoplm1U4V5Z5oqZ4Gx/XI6sSACyPIKgDkGAOC?= =?us-ascii?Q?YfXp23jUQtfC6JgLv5PIZK9VMfEFlRhRjAYI8jYd1HoqX7bqoOFuWGkKcKZx?= =?us-ascii?Q?O8N4lM+/LigNA+XTgEBGmqjcdh/Gn6xFQAJv6YsfQ+BGR2K4oYjsEFKVVl6N?= =?us-ascii?Q?FFbJe+9VwnBd/gumlDrcjjmjjpx9TmlWNSCbeZGHD9CP8nqiEVM3Vq0W/dnz?= =?us-ascii?Q?oIXqE7JXg9fF3smYBFfZsSxZafUEG5VdD8wpMNpsoJyBCaMPd+SO3szbpOeM?= =?us-ascii?Q?NWS9feJxkWsW3OgnNIc5i1TxH9mrvIv82Vi8KjaNxk3R2NOyQEO0a1TpRh5X?= =?us-ascii?Q?9M8Wh00OAUmHCUKT3vf71ImJps6M8fIQn0m9iQymYH4lUjCMCM5SQ1+mJnbF?= =?us-ascii?Q?FhDuwenGVjvxOGo2ST+3HDqWfljg6zsIgXnW1J/OuOKzzRS50m0dGp/JPJ7r?= =?us-ascii?Q?wuB3yTJyQecn/cNgsQBTx1P1BHBFscULpehBCPDu4w72k5TlTPs0h/EdM0xO?= =?us-ascii?Q?80Z2Y8okq1z+D89dWYQL1nTwDnR5aL8l3tdXNtUrAC5TzFoLxYegzg0qRnPZ?= =?us-ascii?Q?Foy3fDB81/thq0Vvg0CxDu9H71lVphGVWX8tSrMF4x/Y0Kb7VhNLe3CkQphz?= =?us-ascii?Q?lZtQRxUjxaASo+HRTDKfXXwuq/J7b+IcAWVP+y2MCQ6WNq+zwK9Zg0NgOhUS?= =?us-ascii?Q?xmdHq4JaWPSGpJJxI6+IBPukW83eD/OV3UZXB1BaJGwLqKgQFO4qsIwqMadb?= =?us-ascii?Q?vSQBDwBv/xfseBb65GLJcUoPZPU4vEtz?= X-Forefront-Antispam-Report: CIP:255.255.255.255;CTRY:;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:PN2P287MB2030.INDP287.PROD.OUTLOOK.COM;PTR:;CAT:NONE;SFS:(13230040)(376014)(52116014)(7416014)(1800799024)(366016)(38350700014);DIR:OUT;SFP:1102; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: =?us-ascii?Q?BWgO7NJxvM9+Xbye0pOVd4yJnOzTeCV+srigMWdSB6wjD/jXrNdF7t0qKTGK?= =?us-ascii?Q?IOxqQ2o4I3xLi63+7U4Fo1YAlc12a1XDSQ9cztuje6shZfkJ1LDdYuips/an?= =?us-ascii?Q?AGHsWwX6Rx22mkjFNaYOx4rvp6rWjlAeKL4iryMIi5Ejz9oFpH6cm6xaKKGx?= =?us-ascii?Q?r0aGCDy2D25UNz8/8+KLE9EmvlQu8GLsr/TranqY0Tsuz+rjUxAhTIUpUBCA?= =?us-ascii?Q?T0gROq5b735Cb+KUpMlAuRmJBX6zUIoTLIdB5P++EOTUc6vL8+eCmpojbDSj?= =?us-ascii?Q?u8V1jva0CPoTneFty4GPZaTikONo4Ywx4l9gBweEAX36NpB/Neq3zjoJ8ybE?= =?us-ascii?Q?+KCFpZ9v8hTzGxT/pzgBbj3OjsTzZOiQwnM7UGLLVnSpk3k9lluszrDj5s6g?= =?us-ascii?Q?/48bTQAahyhRWlSsGRcpN78eylrqJrzMOmdqp1dPcyM0icMEbk4qTJ2OcYVI?= =?us-ascii?Q?p/ewrCINUMmuv3ky1iY5ryt5D1q5P0sBVM0nCTTIf3oIJPBt77Safp9yXx0c?= =?us-ascii?Q?DifUo94Cqf22yizqerzNSw6GGJqwqF9m6nvf73X4mL/SvBBlrifDniPf+jI5?= =?us-ascii?Q?taUzUiTwEWswsEujxr5W/78uXIRgbDmzpySZq6NfNQoZPE2mYulsULb/6zFD?= =?us-ascii?Q?eUncEXDaHecwI8j7js38G65MihuO8KQUF1LZ8rnLqTzpATy9ITBVhU3iMseu?= =?us-ascii?Q?GVfEQd71GLqyoNIPcg1X4oBDaZ4ZsNfxbmDywAdxFnfGmbgojXyBuW7Qk4su?= =?us-ascii?Q?8/ofWtg3Nm7gVrL7UP9fihlo0BhSzhalvfLswS9WcMQwQIbaB3GJOgRtgL78?= =?us-ascii?Q?VIgiIgnyn5uN0dbtdSO8ogBfQOkQD3KjK0pTO9sVIdO8dSM5BJdW0njjFcIL?= =?us-ascii?Q?ymZVz+X8A7C8bRjmGrPvRsZ1yz25ZB1w46ZAyT94srxq1/ipZbjtqOkT+AM+?= =?us-ascii?Q?NfCoEKH4pfemmNAJWNEuh0DwtYY0FrOn4BKnXy9BnLmhJXDZuPwh+z015aoy?= =?us-ascii?Q?dFy2SL8ZAQ4QFhzaj6fWh4VLCxVio098KSHBkpgmGhkNw2Ah5S5nJb3e/zXH?= =?us-ascii?Q?x582WHynWjxdcmwjrKW/VeMYPzFpBipOe42rJkmldTNY8BcWnpm1YrDuYoLQ?= =?us-ascii?Q?FOINq1o5Wz1ZFXLswpNy7VN44n0CxBYB2oqvnfsRF9Hz33HkUazPmV6qXyCR?= =?us-ascii?Q?8clinqYLh+xG3Hvw4Ay36wT2hYszcDuOdo2JtA7r1l6FKwNEU72qH7jmMXE+?= =?us-ascii?Q?A+alDHSA/oaI0mvG+6NUgLug39WJ1g2ZCD0fMuj1OllRNauDR5n/neJPiOwg?= =?us-ascii?Q?Yc6dZ1E5gnN4WlD1EqGH7VUBxxORF8m8QyfBPOL1ICJIfltiPyghEW/rwPbK?= =?us-ascii?Q?M3wxGOQSaLM+67EY4t1EusChUvco0RQLTxEc1OEj6r8dV/DzmeoBe0kf36bw?= =?us-ascii?Q?0Nj1cbC0NzFtjd9s4s/bLFVGPyj2maNYI8klPNEi8jRuDWXSJ1L1klS0Xt1p?= =?us-ascii?Q?LwSK1gLdOHeZY73ccFNAVLkHRrHotJEBa3TQD3dV8k2197RMueGZLQ8UTKkB?= =?us-ascii?Q?Y4QNXx86F3z5XhDnkfT20BLFWAr/ZD/qVakijSdW0DwcEvZYQDWrWW3MZiax?= =?us-ascii?Q?I4PRWFThXkXrpDgWCttEnK11ebDh6lr1NZRxe/a92S1jS59WcwVu+VhF1PhE?= =?us-ascii?Q?k4uOtYdD+uZUT1OEYsXWfpa6U9zJXCtzskN1y2ybOsEF/3+qAyqFO+Z6QDEz?= =?us-ascii?Q?Xbrgpz6vtsVa/B8L6ZJ8Nh0hiUqefuWx1WIkBiibs4NHC2Xd6mwL?= X-OriginatorOrg: siliconsignals.io X-MS-Exchange-CrossTenant-Network-Message-Id: 9fe4a346-860d-4d1e-298a-08de483b4293 X-MS-Exchange-CrossTenant-AuthSource: PN2P287MB2030.INDP287.PROD.OUTLOOK.COM X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-OriginalArrivalTime: 31 Dec 2025 07:07:29.1315 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 7ec5089e-a433-4bd1-a638-82ee62e21d37 X-MS-Exchange-CrossTenant-MailboxType: HOSTED X-MS-Exchange-CrossTenant-UserPrincipalName: 3KfCzBTfkd7aeGSP6LhAuhEmYhQAi0So3H50fXB/mrn3F0xXWuC+WXBc4QNRocYnlRYakHLGirnc/XVKqWGoEfWFvBuOnPeBo1hBnHm8+YYl+9ResWb9eD/KXXt31wva X-MS-Exchange-Transport-CrossTenantHeadersStamped: MAZP287MB0021 Content-Type: text/plain; charset="utf-8" From: Elgin Perumbilly Add bindings for Omnivision OS05B10 sensor. Add MAINTAINERS entry for Omnivision OS05B10 binding documentation Signed-off-by: Elgin Perumbilly Signed-off-by: Himanshu Bhavani Reviewed-by: Vladimir Zapolskiy Reviewed-by: Krzysztof Kozlowski --- .../bindings/media/i2c/ovti,os05b10.yaml | 103 ++++++++++++++++++ MAINTAINERS | 7 ++ 2 files changed, 110 insertions(+) create mode 100644 Documentation/devicetree/bindings/media/i2c/ovti,os05b1= 0.yaml diff --git a/Documentation/devicetree/bindings/media/i2c/ovti,os05b10.yaml = b/Documentation/devicetree/bindings/media/i2c/ovti,os05b10.yaml new file mode 100644 index 000000000000..b76771d81851 --- /dev/null +++ b/Documentation/devicetree/bindings/media/i2c/ovti,os05b10.yaml @@ -0,0 +1,103 @@ +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/media/i2c/ovti,os05b10.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: OmniVision OS05B10 Image Sensor + +maintainers: + - Elgin Perumbilly + +description: + The OmniVision OS05B10 is a 5MP (2592x1944) color CMOS image sensor cont= rolled + through an I2C-compatible SCCB bus. it outputs RAW10/RAW12 format and us= es a + 1/2.78" optical format. + +properties: + compatible: + const: ovti,os05b10 + + reg: + maxItems: 1 + + clocks: + items: + - description: XCLK clock + + avdd-supply: + description: Analog Domain Power Supply (2.8v) + + dovdd-supply: + description: I/O Domain Power Supply (1.8v) + + dvdd-supply: + description: Digital Domain Power Supply (1.2v) + + reset-gpios: + maxItems: 1 + description: Reset Pin GPIO Control (active low) + + port: + description: MIPI CSI-2 transmitter port + $ref: /schemas/graph.yaml#/$defs/port-base + additionalProperties: false + + properties: + endpoint: + $ref: /schemas/media/video-interfaces.yaml# + unevaluatedProperties: false + + properties: + data-lanes: + oneOf: + - items: + - const: 1 + - const: 2 + - const: 3 + - const: 4 + - items: + - const: 1 + - const: 2 + required: + - data-lanes + - link-frequencies + +required: + - compatible + - reg + - clocks + - avdd-supply + - dovdd-supply + - dvdd-supply + - port + +additionalProperties: false + +examples: + - | + #include + + i2c { + #address-cells =3D <1>; + #size-cells =3D <0>; + + camera-sensor@36 { + compatible =3D "ovti,os05b10"; + reg =3D <0x36>; + clocks =3D <&os05b10_clk>; + reset-gpios =3D <&gpio1 7 GPIO_ACTIVE_LOW>; + + avdd-supply =3D <&os05b10_avdd_2v8>; + dvdd-supply =3D <&os05b10_dvdd_1v2>; + dovdd-supply =3D <&os05b10_dovdd_1v8>; + + port { + cam_out: endpoint { + remote-endpoint =3D <&mipi_in_cam>; + data-lanes =3D <1 2 3 4>; + link-frequencies =3D /bits/ 64 <600000000>; + }; + }; + }; + }; diff --git a/MAINTAINERS b/MAINTAINERS index 663e86eb9ff1..c85915d5d20e 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -19234,6 +19234,13 @@ T: git git://linuxtv.org/media_tree.git F: Documentation/devicetree/bindings/media/i2c/ovti,og0ve1b.yaml F: drivers/media/i2c/og0ve1b.c +OMNIVISION OS05B10 SENSOR DRIVER +M: Himanshu Bhavani +M: Elgin Perumbilly +L: linux-media@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/media/i2c/ovti,os05b10.yaml + OMNIVISION OV01A10 SENSOR DRIVER M: Bingbu Cao L: linux-media@vger.kernel.org -- 2.34.1 From nobody Mon Feb 9 21:00:32 2026 Received: from MA0PR01CU012.outbound.protection.outlook.com (mail-southindiaazon11021089.outbound.protection.outlook.com [40.107.57.89]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 5E5D73101CD; Wed, 31 Dec 2025 07:07:41 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=40.107.57.89 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1767164865; cv=fail; b=ppu3SEEo9Z+IOH3JYut4PMVrfQQyxHn/x4+rVJll4Z8RzD8UDnJvCqVenNBZkGt/1Y7O+ZPkGM9zjFZCum3R2jSsTxwywq3jUMJkIBaxbZH0LlHFE9TVM3FAro1wo/EPRaQcR9oCeaCepXTaUyUFB2nyEdNXpeY39DggiyYI5FU= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1767164865; c=relaxed/simple; bh=NCYZ+dHtUjkunUR5jrH4IroqKF8ZkUGnOoC9J+InKY8=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: Content-Type:MIME-Version; b=Nz9NRMQ2Y4BpDFT/NVOrp1m8PGOjieZ6TZ01g5RCQtbejqRPdAM+3yKtNSZ7M7kXa7M2Naimx5rctSA4M5L+rGDRNGz7IE37KpHINqUQKlgoBBQcVPwXCgRK8xWJFE8S/AkVagYOAM7XGUtuWi9iNiSCA+SY/U//OuecnA+Sg2U= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=siliconsignals.io; spf=pass smtp.mailfrom=siliconsignals.io; dkim=pass (2048-bit key) header.d=siliconsignals.io header.i=@siliconsignals.io header.b=NZhIXtlp; arc=fail smtp.client-ip=40.107.57.89 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=siliconsignals.io Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=siliconsignals.io Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=siliconsignals.io header.i=@siliconsignals.io header.b="NZhIXtlp" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=RSys1GTFhZjmWwz7j2/fj6Hc+24tV4lHWeFx2CRoZcK3KhcVx8L/Mn2/GAVCy1wI/QAEzQ7qrksqrq0Ryz9i5Bk1ApwgII04b160heqTWFSons2vaezW0z+f97A3Fq26kctNO5Zr4V4j/+dfiHc2M+UbX9vv4eroBvJ094eWcCaBAOgBRsmwqlFQ6vlOt904QQad/BrcgtFbNdWXtWLq1p1LazwRg308uB9JFzCi4f0Jd9kuNOKtTs7HXGImoEbN874i9Aj8kHh3F+63suKlErZ7P1lsbYmxYTx9LUrq3IuRpy9G1mIbgyHSrHmTU9eQYdDwjyAjd5j+iW1mB07Jrw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector10001; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=qZGxYQvip4GKqz37NPp+KABLi2JXjCAGqEi9RVvU2QI=; b=Emmn20LXKZLlcg327Z3SLIPSTzFMZGshhw1YdK3S5kov8aK//NwLC/HtfSc8b1QAR6Ybxy2Fgbrletf0CloLMtDvSmHDaKY/KsIBXIAjSSNfdFHIJ+oUVz2myVyH8PTSpjUl2NmWsd9+byIR5cCCNVkkNR57zmEmSfWWCgb5By6RYCXEj968sFOamlKct3ZTeEKdU0XSLR9AGORA8fWGF/sQC0RAOU0IaZ2K+Up+3G6MFSCD4pkRUlsfDfj9BPUGbhJXI9iqoA22nWcYw1igaAMObJBTPzKqIk0FVmESYJyCFsZxbZuqCUbMgPs7D5t0E31cskPnhwtTVXXzIDvpnQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=siliconsignals.io; dmarc=pass action=none header.from=siliconsignals.io; dkim=pass header.d=siliconsignals.io; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=siliconsignals.io; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=qZGxYQvip4GKqz37NPp+KABLi2JXjCAGqEi9RVvU2QI=; b=NZhIXtlpFt+oVy4xJ950Xl/rz4nxR7XmCl65LCr36JJNRoGHS48DjhbhyGQlHEOcHi8ymgAeItVZAdZ1fDQ/WwtnQIXGA+rl314nkY0celX+Olf2wBl67zfPCP2YhqPGUkU7gp2W+2sNotcMje5Bq8INUjZRBh6tuQ9PjU5loebYF9+i1vjpW2A2GxO/lIh7BVb8X6cw5779DwejU/LffLJEC4IhRhPn/a8EuJOq5RZiqxKsHMPvzSFYXtaQzEr8vzw+rE6hTgurCtFlgWRlr8ibjlLRw8UIf4UFoX0OG7X4IXul4NFoDuTramiH/Q9C0fn4GSlVhcBF6XM2nRjnuQ== Authentication-Results: dkim=none (message not signed) header.d=none;dmarc=none action=none header.from=siliconsignals.io; Received: from PN2P287MB2030.INDP287.PROD.OUTLOOK.COM (2603:1096:c01:1c9::8) by MAZP287MB0021.INDP287.PROD.OUTLOOK.COM (2603:1096:a01:40::6) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.9478.4; Wed, 31 Dec 2025 07:07:38 +0000 Received: from PN2P287MB2030.INDP287.PROD.OUTLOOK.COM ([fe80::85bb:6572:ae6c:5a15]) by PN2P287MB2030.INDP287.PROD.OUTLOOK.COM ([fe80::85bb:6572:ae6c:5a15%3]) with mapi id 15.20.9456.008; Wed, 31 Dec 2025 07:07:38 +0000 From: Himanshu Bhavani To: robh@kernel.org, krzk+dt@kernel.org, sakari.ailus@linux.intel.com Cc: Himanshu Bhavani , Elgin Perumbilly , Vladimir Zapolskiy , Mehdi Djait , Mauro Carvalho Chehab , Conor Dooley , Hans Verkuil , Hans de Goede , =?UTF-8?q?Andr=C3=A9=20Apitzsch?= , Laurent Pinchart , Dongcheng Yan , Benjamin Mugnier , Sylvain Petinot , "Bryan O'Donoghue" , Heimir Thor Sverrisson , Jingjing Xiong , linux-media@vger.kernel.org, devicetree@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH v7 2/2] media: i2c: add os05b10 image sensor driver Date: Wed, 31 Dec 2025 12:36:38 +0530 Message-Id: <20251231070645.16434-3-himanshu.bhavani@siliconsignals.io> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20251231070645.16434-1-himanshu.bhavani@siliconsignals.io> References: <20251231070645.16434-1-himanshu.bhavani@siliconsignals.io> Content-Transfer-Encoding: quoted-printable X-ClientProxiedBy: PN3PR01CA0125.INDPRD01.PROD.OUTLOOK.COM (2603:1096:c01:96::11) To PN2P287MB2030.INDP287.PROD.OUTLOOK.COM (2603:1096:c01:1c9::8) Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: PN2P287MB2030:EE_|MAZP287MB0021:EE_ X-MS-Office365-Filtering-Correlation-Id: b952a7fe-4119-4a74-45b5-08de483b484f X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|376014|52116014|7416014|1800799024|366016|38350700014; X-Microsoft-Antispam-Message-Info: =?us-ascii?Q?S32iDiRe0/toWbYRXZo+SnK7wHyaJK0VLPyYJ3lkqc3Gk49AwV4aedboM2W0?= =?us-ascii?Q?+Ji6NfkpLyOd7kMhjmIVZKdXT9NZ35oB8yuwO8UlGkQFqYrsWFHhtdtVix6z?= =?us-ascii?Q?u4VcFF7I2O78mNS+H5GcBU/nKiXdUXLFrFpmOwkrBlIFwTe6LqGi9WdchBAg?= =?us-ascii?Q?hdTcspgUJtZ790Atb5f2C8jSrcPhinuCCGUr68jGdj0db9jm8d/Hx6tSkHeY?= =?us-ascii?Q?n9zmMqPILEEkC3KiTOSn6Uj0EbJWQM1SNeU7Ah7j57rfP04WsCfD7ei2j2fg?= =?us-ascii?Q?DTypojof4Jylr9wFOsGRO/m1OJiMhedP63ytTfi51l3SvWO1PV3MhIZxK9Rt?= =?us-ascii?Q?v/IdkpqsLnZQjksO5KH4U1C4kYDGixoPdzL6Rtoc3tk1LgejZ9cm8cPzoeZS?= =?us-ascii?Q?Dv12a9KlbXWgxQMDdqh6cFUmbeBPzBhHaRZvcz2niOVt9INWhGzVNP01w47M?= =?us-ascii?Q?kjAWTr0llcqwV4xORhYc2gpYL61iWru7KUjGtNpMaHxt6iH0/Nu9MMzxe+VQ?= =?us-ascii?Q?JlWMpY2fjSSWMMkncc4E0UCFZSxfXghYuHJLZ1n1gK0+/34zpN4JZXoHiz1a?= =?us-ascii?Q?LJX8LsJpgkF1/+2J7O7KzbAdt2xwUN24t0u6Xvjfg+x1GyO1lmkhKPY5iFsb?= =?us-ascii?Q?xeoXV7+jP9UOvb+eJyzkYxgHdBVsTCU4lA/J8wq8rI2Z7oe5t8nWZLw85bmS?= =?us-ascii?Q?xq+I1gXcUgmT5fn3ASezqCsCkEW8gltPp608Ki50BvWshk1tu+we4Q+o4oKW?= =?us-ascii?Q?4lH09xRq+q+D7oGJ5Kp60cuik2G9HUs6WZkw+CkljndxEs2rUSI8WKdzLHuG?= =?us-ascii?Q?v2xymPtLSEbUijMexyJljnRsZYEc6FFyrVqy9bUZ/ckwaDiflrYoOorHGq4n?= =?us-ascii?Q?NPtyx6JFNfVx74Nqn+/VLozvUmZXUIVfhSx6nVF5tPIkFWj0zSqrmfW9Gx4m?= =?us-ascii?Q?YmQW8y5Z0V8SWMqU55eAXXxlQNQNFT0l+mDxSJGRoauK+0I4+B6CBNYpKrOL?= =?us-ascii?Q?hlZcOuv1ZglsrBdlEYWzbrFkpj9CPAVrUcjvWyeWR0V6reILAtRG7YfnJcEC?= =?us-ascii?Q?dXoBRpDmTcZzo/hw4kJhf+Y8TPwdBlz2Dj+hw3JtRutbunboWoIXmFv8nZba?= =?us-ascii?Q?PnGYOgWkN0dq/JQAVoQhmGd1bBbAjRz4uEo7U5PXUY1S9GKDm70RqiqroVdF?= =?us-ascii?Q?bQrq+FiHEC/Trhu1n99IWu1iCwsczpOv6DaqBapfG6U1xI9lAqrCdMVNMvfz?= =?us-ascii?Q?VLCtP9jNEb+4r2Iy4nXki0v5afcxRKyWY3tJx8373X59w7tKeFw/lBoJ4UF2?= =?us-ascii?Q?8pv59yWl++8KvUy03U5IRyQSEkOhEpDxKNkgDpVx79Ev0fK5RWquP+FNFC7u?= =?us-ascii?Q?IY5pP7MqaGzSQJuWRrabr7RabBDl5WnqBmDj7Po5dbJa97cQspDbetEJEJKe?= =?us-ascii?Q?r7o2LfVNicqxXJioR6/pPqvZAu0JqMPCPZOaWsmWIa5NYonvqHlAU3SCwxUa?= =?us-ascii?Q?lmJOd7cfW07GJGTBZL6S+1XrwFGKFV2s6DNH?= X-Forefront-Antispam-Report: CIP:255.255.255.255;CTRY:;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:PN2P287MB2030.INDP287.PROD.OUTLOOK.COM;PTR:;CAT:NONE;SFS:(13230040)(376014)(52116014)(7416014)(1800799024)(366016)(38350700014);DIR:OUT;SFP:1102; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: =?us-ascii?Q?YU5y8A2O2Kd5DDuEBuiI2Muoh79BCLxadSQtpnPWXrRkvzFa59uxUQzPYV8K?= =?us-ascii?Q?laUaZijnGQH4YyU3sC8NVqKXbMb//MOKCA8bOHVowYM7PFFXtoO4iD8isCx2?= =?us-ascii?Q?j7517BFYjJNtNmEQQni9soTRrb/H76AL4uDhCw4QEuuJ2/wR1AnupoYikoxc?= =?us-ascii?Q?dvpriSHFTbt8Uhgoz7oC2YivB4haTcpdBiifFfJtmzTfmDQgf/JCn/W1AXKX?= =?us-ascii?Q?L+g2xPKidWnYgAkL9tHkkq8f72x0BUoGlXnCs8+GGA7sH/HXZQwHiMcguuYA?= =?us-ascii?Q?LxEkn6JYmt7upA70GZ38AlTCmIzZW7901IeF9utBdtk7Jhd4ImxuFYCcwrPb?= =?us-ascii?Q?fxIeZgGkjQSHY1j2lvmK9KeyjL5qg2VqyVmy12gACT7ENa6vb7RfpLtK8iFZ?= =?us-ascii?Q?pneB2lVK3XL17GHh0Gh4yKaxP2TZsML8zgz92FN1huxogpMwofdGDcoxCvpa?= =?us-ascii?Q?TJDFUv9a7Hj9uRUB+Fv/T/p6/kijbVNSTiQzvNAnwZ5/+c6cpEYKWAqsXYkp?= =?us-ascii?Q?GGukV11vBaab1ZDdX1ce8nKqkKyaW4UbeRwbsmLdejZ5Z1NLAMd5UGhUz9OA?= =?us-ascii?Q?Gg9u0TJmbZ4WoNJMQw1sIm8qcrik14LiJ/zWYMH/W3mvM7+CQEMs3u1B4pje?= =?us-ascii?Q?HYz2LA4Itni08uWaijnUOpj7+a/CWzEdSxHsj8+FgillogIunS8FfJR+iKea?= =?us-ascii?Q?xcNpVHk/aFRX5TRQoPuUTLYWmQEwVUCgE+pmp9geGnFpcPjq/pAOfwo6ei5X?= =?us-ascii?Q?7xOYjOBK44UJvKuHSJ5CYQC0yL9+HCGEp/NSns2IXW9d3jVDeMy9WU7wb4up?= =?us-ascii?Q?HcKkNxoSSlr84wIGNcd4H8Um8UFT4hRar9zHdjtQd+6GwZQCebHYU59D2E7U?= =?us-ascii?Q?ymC9UxMGsgD4Ri/F5mMhbxrFJ/aM1WwEQMglD1H/47sf7mrCSXdn6ekjGiRs?= =?us-ascii?Q?ZdmCDsUzWNM4XixqwIIUC7rfCm+l5OzvadyT3w2D9mqoInUob7zN2E2D3yeQ?= =?us-ascii?Q?3dAvEymwxa7u9aGUdgCSHeuPO2PSU8K7YikVEfmTrCycSioRPeoBJL0E+aL0?= =?us-ascii?Q?rXeCYWKIw2fnlYoA+3S7+Z9pfi2HlrHT578yGXt0/MHUdGdQCIAfqQKzNlnu?= =?us-ascii?Q?gV5jzFBL443JrCb2lUMD6Bdb5z5ngnVd47hZhwhLMV6SPPtxT2YtIcpwkeoW?= =?us-ascii?Q?Z1UcLuhVzdpCVQCe+f1VaVwlIbPnH97MhCjCuJylWAApo0/Tflu6slm1W4sS?= =?us-ascii?Q?WWI7sPJN3ESXuKIksqlbAmXYnEOETVEPmVh+iyBjoaeW+xBqkBgswWU9zSbO?= =?us-ascii?Q?OCa3ufEBTE0kY5Hr7WfUsA1Uer/eL/4KXgYnVGDm/8TSu/3IXyJ5E8PB8a+/?= =?us-ascii?Q?A+fvIaMCr1GpFuATTkosP8pWVh/KdueRQAD+HltNqMYlDPzVnfZf0GHIb0RH?= =?us-ascii?Q?My1Crj6hpmwVL24wKrgSpFHk2uiAI82w4g5wLEAwloglX1k0ND54Db98wxD4?= =?us-ascii?Q?iUfWw7IHPb3ttCPDyGqPaWU40szeUYHXHbx1muWGyggBRrJxiHENC1tVdabW?= =?us-ascii?Q?/FMtRPqEC0uSRj5m3s+PihJux35jsBFdLfDc5x9+mNPErwzQRi6x+OZosrBs?= =?us-ascii?Q?0s5OyvlqbXc8yJzDEVpXzI5FrYEJ+BeNz5ozw+yW5PmKh8m8ikXwGoQS+5YE?= =?us-ascii?Q?uEyATVdEB5f14lSOsI3lWPwbkMWd3J5mG9szBS7AoINPGzZo4R3BVOedBWis?= =?us-ascii?Q?7cfoGvQrXd8NUyEnMraHmnc/B5NRHRyH9X8at3qWLPYG4UTtMrNS?= X-OriginatorOrg: siliconsignals.io X-MS-Exchange-CrossTenant-Network-Message-Id: b952a7fe-4119-4a74-45b5-08de483b484f X-MS-Exchange-CrossTenant-AuthSource: PN2P287MB2030.INDP287.PROD.OUTLOOK.COM X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-OriginalArrivalTime: 31 Dec 2025 07:07:38.8040 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 7ec5089e-a433-4bd1-a638-82ee62e21d37 X-MS-Exchange-CrossTenant-MailboxType: HOSTED X-MS-Exchange-CrossTenant-UserPrincipalName: +8SdGF9sRYG4uMyRJywGcq+P6NlJEBBo2j/aViRrUWmdrQhIe4s7FskzTu2ukWEfhwV0GBMW+3YFsHEzxk7KZvreELO2rkT/vwYCw7mTaENbrqXe+RYhvp8M5Qw6XmjW X-MS-Exchange-Transport-CrossTenantHeadersStamped: MAZP287MB0021 Content-Type: text/plain; charset="utf-8" Add a v4l2 subdevice driver for the Omnivision OS05B10 sensor. The Omnivision OS05B10 image sensor with an active array size of 2592 x 1944. The following features are supported: - Manual exposure an gain control support - vblank/hblank control support - Supported resolution: 2592 x 1944 @ 60fps (SBGGR10) Co-developed-by: Elgin Perumbilly Signed-off-by: Elgin Perumbilly Signed-off-by: Himanshu Bhavani Reviewed-by: Vladimir Zapolskiy Reviewed-by: Mehdi Djait --- MAINTAINERS | 1 + drivers/media/i2c/Kconfig | 10 + drivers/media/i2c/Makefile | 1 + drivers/media/i2c/os05b10.c | 1115 +++++++++++++++++++++++++++++++++++ 4 files changed, 1127 insertions(+) create mode 100644 drivers/media/i2c/os05b10.c diff --git a/MAINTAINERS b/MAINTAINERS index c85915d5d20e..c48d04ca38d1 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -19240,6 +19240,7 @@ M: Elgin Perumbilly L: linux-media@vger.kernel.org S: Maintained F: Documentation/devicetree/bindings/media/i2c/ovti,os05b10.yaml +F: drivers/media/i2c/os05b10.c OMNIVISION OV01A10 SENSOR DRIVER M: Bingbu Cao diff --git a/drivers/media/i2c/Kconfig b/drivers/media/i2c/Kconfig index 4b4db8c4f496..9800ba50b9a6 100644 --- a/drivers/media/i2c/Kconfig +++ b/drivers/media/i2c/Kconfig @@ -371,6 +371,16 @@ config VIDEO_OG0VE1B To compile this driver as a module, choose M here: the module will be called og0ve1b. +config VIDEO_OS05B10 + tristate "OmniVision OS05B10 sensor support" + select V4L2_CCI_I2C + help + This is a Video4Linux2 sensor driver for Omnivision + OS05B10 camera sensor. + + To compile this driver as a module, choose M here: the + module will be called os05b10. + config VIDEO_OV01A10 tristate "OmniVision OV01A10 sensor support" help diff --git a/drivers/media/i2c/Makefile b/drivers/media/i2c/Makefile index c5f17602454f..561d37939875 100644 --- a/drivers/media/i2c/Makefile +++ b/drivers/media/i2c/Makefile @@ -84,6 +84,7 @@ obj-$(CONFIG_VIDEO_MT9V032) +=3D mt9v032.o obj-$(CONFIG_VIDEO_MT9V111) +=3D mt9v111.o obj-$(CONFIG_VIDEO_OG01A1B) +=3D og01a1b.o obj-$(CONFIG_VIDEO_OG0VE1B) +=3D og0ve1b.o +obj-$(CONFIG_VIDEO_OS05B10) +=3D os05b10.o obj-$(CONFIG_VIDEO_OV01A10) +=3D ov01a10.o obj-$(CONFIG_VIDEO_OV02A10) +=3D ov02a10.o obj-$(CONFIG_VIDEO_OV02C10) +=3D ov02c10.o diff --git a/drivers/media/i2c/os05b10.c b/drivers/media/i2c/os05b10.c new file mode 100644 index 000000000000..7fa6e60d5d58 --- /dev/null +++ b/drivers/media/i2c/os05b10.c @@ -0,0 +1,1115 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * V4L2 Support for the os05b10 + * + * Copyright (C) 2025 Silicon Signals Pvt. Ltd. + * + * Inspired from imx219, ov2735 camera drivers. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +#define OS05B10_XCLK_FREQ (24 * HZ_PER_MHZ) + +#define OS05B10_REG_CHIP_ID CCI_REG24(0x300A) +#define OS05B10_CHIP_ID 0x530641 + +#define OS05B10_REG_CTRL_MODE CCI_REG8(0x0100) +#define OS05B10_MODE_STANDBY 0x00 +#define OS05B10_MODE_STREAMING 0x01 + +#define OS05B10_REG_VTS CCI_REG16(0x380E) +#define OS05B10_VTS_MAX 0xFFFF + +#define OS05B10_REG_HTS CCI_REG16(0x380C) + +#define OS05B10_REG_ANALOG_GAIN CCI_REG16(0x3508) +#define OS05B10_ANALOG_GAIN_MIN 0x80 +#define OS05B10_ANALOG_GAIN_MAX 0x7C0 +#define OS05B10_ANALOG_GAIN_STEP 1 +#define OS05B10_ANALOG_GAIN_DEFAULT 0x80 + +#define OS05B10_REG_EXPOSURE CCI_REG24(0x3500) +#define OS05B10_EXPOSURE_MIN 2 +#define OS05B10_EXPOSURE_STEP 1 +#define OS05B10_EXPOSURE_MARGIN 8 + +#define OS05B10_PIXEL_RATE (480 * HZ_PER_MHZ) +#define OS05B10_LINK_FREQ_600MHZ (600 * HZ_PER_MHZ) + +static const struct v4l2_rect os05b10_native_area =3D { + .top =3D 0, + .left =3D 0, + .width =3D 2608, + .height =3D 1960, +}; + +static const struct v4l2_rect os05b10_active_area =3D { + .top =3D 8, + .left =3D 8, + .width =3D 2592, + .height =3D 1944, +}; + +static const char * const os05b10_supply_name[] =3D { + "avdd", /* Analog supply */ + "dovdd", /* Digital IO */ + "dvdd", /* Digital core */ +}; + +static const struct cci_reg_sequence os05b10_common_regs[] =3D { + { CCI_REG8(0x0301), 0x44 }, + { CCI_REG8(0x0303), 0x02 }, + { CCI_REG8(0x0305), 0x32 }, + { CCI_REG8(0x0306), 0x00 }, + { CCI_REG8(0x0325), 0x3b }, + { CCI_REG8(0x3002), 0x21 }, + { CCI_REG8(0x3016), 0x72 }, + { CCI_REG8(0x301e), 0xb4 }, + { CCI_REG8(0x301f), 0xd0 }, + { CCI_REG8(0x3021), 0x03 }, + { CCI_REG8(0x3022), 0x01 }, + { CCI_REG8(0x3107), 0xa1 }, + { CCI_REG8(0x3108), 0x7d }, + { CCI_REG8(0x3109), 0xfc }, + { CCI_REG8(0x3500), 0x00 }, + { CCI_REG8(0x3501), 0x07 }, + { CCI_REG8(0x3502), 0xb6 }, + { CCI_REG8(0x3503), 0x88 }, + { CCI_REG8(0x3508), 0x00 }, + { CCI_REG8(0x3509), 0x80 }, + { CCI_REG8(0x350a), 0x04 }, + { CCI_REG8(0x350b), 0x00 }, + { CCI_REG8(0x350c), 0x00 }, + { CCI_REG8(0x350d), 0x80 }, + { CCI_REG8(0x350e), 0x04 }, + { CCI_REG8(0x350f), 0x00 }, + { CCI_REG8(0x3510), 0x00 }, + { CCI_REG8(0x3511), 0x00 }, + { CCI_REG8(0x3512), 0x20 }, + { CCI_REG8(0x3600), 0x4d }, + { CCI_REG8(0x3601), 0x08 }, + { CCI_REG8(0x3610), 0x87 }, + { CCI_REG8(0x3611), 0x24 }, + { CCI_REG8(0x3614), 0x4c }, + { CCI_REG8(0x3620), 0x0c }, + { CCI_REG8(0x3632), 0x80 }, + { CCI_REG8(0x3633), 0x00 }, + { CCI_REG8(0x3636), 0xcc }, + { CCI_REG8(0x3637), 0x27 }, + { CCI_REG8(0x3660), 0x00 }, + { CCI_REG8(0x3662), 0x10 }, + { CCI_REG8(0x3665), 0x00 }, + { CCI_REG8(0x3666), 0x00 }, + { CCI_REG8(0x366a), 0x14 }, + { CCI_REG8(0x3670), 0x0b }, + { CCI_REG8(0x3671), 0x0b }, + { CCI_REG8(0x3672), 0x0b }, + { CCI_REG8(0x3673), 0x0b }, + { CCI_REG8(0x3678), 0x2b }, + { CCI_REG8(0x367a), 0x11 }, + { CCI_REG8(0x367b), 0x11 }, + { CCI_REG8(0x367c), 0x11 }, + { CCI_REG8(0x367d), 0x11 }, + { CCI_REG8(0x3681), 0xff }, + { CCI_REG8(0x3682), 0x86 }, + { CCI_REG8(0x3683), 0x44 }, + { CCI_REG8(0x3684), 0x24 }, + { CCI_REG8(0x3685), 0x00 }, + { CCI_REG8(0x368a), 0x00 }, + { CCI_REG8(0x368d), 0x2b }, + { CCI_REG8(0x368e), 0x2b }, + { CCI_REG8(0x3690), 0x00 }, + { CCI_REG8(0x3691), 0x0b }, + { CCI_REG8(0x3692), 0x0b }, + { CCI_REG8(0x3693), 0x0b }, + { CCI_REG8(0x3694), 0x0b }, + { CCI_REG8(0x369d), 0x68 }, + { CCI_REG8(0x369e), 0x34 }, + { CCI_REG8(0x369f), 0x1b }, + { CCI_REG8(0x36a0), 0x0f }, + { CCI_REG8(0x36a1), 0x77 }, + { CCI_REG8(0x36b0), 0x30 }, + { CCI_REG8(0x36b2), 0x00 }, + { CCI_REG8(0x36b3), 0x00 }, + { CCI_REG8(0x36b4), 0x00 }, + { CCI_REG8(0x36b5), 0x00 }, + { CCI_REG8(0x36b6), 0x00 }, + { CCI_REG8(0x36b7), 0x00 }, + { CCI_REG8(0x36b8), 0x00 }, + { CCI_REG8(0x36b9), 0x00 }, + { CCI_REG8(0x36ba), 0x00 }, + { CCI_REG8(0x36bb), 0x00 }, + { CCI_REG8(0x36bc), 0x00 }, + { CCI_REG8(0x36bd), 0x00 }, + { CCI_REG8(0x36be), 0x00 }, + { CCI_REG8(0x36bf), 0x00 }, + { CCI_REG8(0x36c0), 0x01 }, + { CCI_REG8(0x36c1), 0x00 }, + { CCI_REG8(0x36c2), 0x00 }, + { CCI_REG8(0x36c3), 0x00 }, + { CCI_REG8(0x36c4), 0x00 }, + { CCI_REG8(0x36c5), 0x00 }, + { CCI_REG8(0x36c6), 0x00 }, + { CCI_REG8(0x36c7), 0x00 }, + { CCI_REG8(0x36c8), 0x00 }, + { CCI_REG8(0x36c9), 0x00 }, + { CCI_REG8(0x36ca), 0x0e }, + { CCI_REG8(0x36cb), 0x0e }, + { CCI_REG8(0x36cc), 0x0e }, + { CCI_REG8(0x36cd), 0x0e }, + { CCI_REG8(0x36ce), 0x0c }, + { CCI_REG8(0x36cf), 0x0c }, + { CCI_REG8(0x36d0), 0x0c }, + { CCI_REG8(0x36d1), 0x0c }, + { CCI_REG8(0x36d2), 0x00 }, + { CCI_REG8(0x36d3), 0x08 }, + { CCI_REG8(0x36d4), 0x10 }, + { CCI_REG8(0x36d5), 0x10 }, + { CCI_REG8(0x36d6), 0x00 }, + { CCI_REG8(0x36d7), 0x08 }, + { CCI_REG8(0x36d8), 0x10 }, + { CCI_REG8(0x36d9), 0x10 }, + { CCI_REG8(0x3701), 0x1d }, + { CCI_REG8(0x3703), 0x2a }, + { CCI_REG8(0x3704), 0x05 }, + { CCI_REG8(0x3709), 0x57 }, + { CCI_REG8(0x370b), 0x63 }, + { CCI_REG8(0x3706), 0x28 }, + { CCI_REG8(0x370a), 0x00 }, + { CCI_REG8(0x370b), 0x63 }, + { CCI_REG8(0x370e), 0x0c }, + { CCI_REG8(0x370f), 0x1c }, + { CCI_REG8(0x3710), 0x00 }, + { CCI_REG8(0x3713), 0x00 }, + { CCI_REG8(0x3714), 0x24 }, + { CCI_REG8(0x3716), 0x24 }, + { CCI_REG8(0x371a), 0x1e }, + { CCI_REG8(0x3724), 0x09 }, + { CCI_REG8(0x3725), 0xb2 }, + { CCI_REG8(0x372b), 0x54 }, + { CCI_REG8(0x3730), 0xe1 }, + { CCI_REG8(0x3735), 0x80 }, + { CCI_REG8(0x3739), 0x10 }, + { CCI_REG8(0x373f), 0xb0 }, + { CCI_REG8(0x3740), 0x28 }, + { CCI_REG8(0x3741), 0x21 }, + { CCI_REG8(0x3742), 0x21 }, + { CCI_REG8(0x3743), 0x21 }, + { CCI_REG8(0x3744), 0x63 }, + { CCI_REG8(0x3745), 0x5a }, + { CCI_REG8(0x3746), 0x5a }, + { CCI_REG8(0x3747), 0x5a }, + { CCI_REG8(0x3748), 0x00 }, + { CCI_REG8(0x3749), 0x00 }, + { CCI_REG8(0x374a), 0x00 }, + { CCI_REG8(0x374b), 0x00 }, + { CCI_REG8(0x3756), 0x00 }, + { CCI_REG8(0x3757), 0x0e }, + { CCI_REG8(0x375d), 0x84 }, + { CCI_REG8(0x3760), 0x11 }, + { CCI_REG8(0x3767), 0x08 }, + { CCI_REG8(0x376f), 0x42 }, + { CCI_REG8(0x3771), 0x00 }, + { CCI_REG8(0x3773), 0x01 }, + { CCI_REG8(0x3774), 0x02 }, + { CCI_REG8(0x3775), 0x12 }, + { CCI_REG8(0x3776), 0x02 }, + { CCI_REG8(0x377b), 0x40 }, + { CCI_REG8(0x377c), 0x00 }, + { CCI_REG8(0x377d), 0x0c }, + { CCI_REG8(0x3782), 0x02 }, + { CCI_REG8(0x3787), 0x24 }, + { CCI_REG8(0x378a), 0x01 }, + { CCI_REG8(0x378d), 0x00 }, + { CCI_REG8(0x3790), 0x1f }, + { CCI_REG8(0x3791), 0x58 }, + { CCI_REG8(0x3795), 0x24 }, + { CCI_REG8(0x3796), 0x01 }, + { CCI_REG8(0x3798), 0x40 }, + { CCI_REG8(0x379c), 0x00 }, + { CCI_REG8(0x379d), 0x00 }, + { CCI_REG8(0x379e), 0x00 }, + { CCI_REG8(0x379f), 0x01 }, + { CCI_REG8(0x37a1), 0x10 }, + { CCI_REG8(0x37a6), 0x00 }, + { CCI_REG8(0x37ab), 0x0e }, + { CCI_REG8(0x37ac), 0xa0 }, + { CCI_REG8(0x37be), 0x0a }, + { CCI_REG8(0x37bf), 0x05 }, + { CCI_REG8(0x37bb), 0x02 }, + { CCI_REG8(0x37bf), 0x05 }, + { CCI_REG8(0x37c2), 0x04 }, + { CCI_REG8(0x37c4), 0x11 }, + { CCI_REG8(0x37c5), 0x80 }, + { CCI_REG8(0x37c6), 0x14 }, + { CCI_REG8(0x37c7), 0x08 }, + { CCI_REG8(0x37c8), 0x42 }, + { CCI_REG8(0x37cd), 0x17 }, + { CCI_REG8(0x37ce), 0x01 }, + { CCI_REG8(0x37d8), 0x02 }, + { CCI_REG8(0x37d9), 0x08 }, + { CCI_REG8(0x37dc), 0x01 }, + { CCI_REG8(0x37e0), 0x0c }, + { CCI_REG8(0x37e1), 0x20 }, + { CCI_REG8(0x37e2), 0x10 }, + { CCI_REG8(0x37e3), 0x04 }, + { CCI_REG8(0x37e4), 0x28 }, + { CCI_REG8(0x37e5), 0x02 }, + { CCI_REG8(0x37ef), 0x00 }, + { CCI_REG8(0x37f4), 0x00 }, + { CCI_REG8(0x37f5), 0x00 }, + { CCI_REG8(0x37f6), 0x00 }, + { CCI_REG8(0x37f7), 0x00 }, + { CCI_REG8(0x3800), 0x01 }, + { CCI_REG8(0x3801), 0x30 }, + { CCI_REG8(0x3802), 0x00 }, + { CCI_REG8(0x3803), 0x00 }, + { CCI_REG8(0x3804), 0x0b }, + { CCI_REG8(0x3805), 0x5f }, + { CCI_REG8(0x3806), 0x07 }, + { CCI_REG8(0x3807), 0xa7 }, + { CCI_REG8(0x3808), 0x0a }, + { CCI_REG8(0x3809), 0x20 }, + { CCI_REG8(0x380a), 0x07 }, + { CCI_REG8(0x380b), 0x98 }, + { CCI_REG8(0x380c), 0x06 }, + { CCI_REG8(0x380d), 0xd0 }, + { CCI_REG8(0x380e), 0x07 }, + { CCI_REG8(0x380f), 0xd6 }, + { CCI_REG8(0x3810), 0x00 }, + { CCI_REG8(0x3811), 0x08 }, + { CCI_REG8(0x3812), 0x00 }, + { CCI_REG8(0x3813), 0x08 }, + { CCI_REG8(0x3814), 0x01 }, + { CCI_REG8(0x3815), 0x01 }, + { CCI_REG8(0x3816), 0x01 }, + { CCI_REG8(0x3817), 0x01 }, + { CCI_REG8(0x3818), 0x00 }, + { CCI_REG8(0x3819), 0x00 }, + { CCI_REG8(0x381a), 0x00 }, + { CCI_REG8(0x381b), 0x01 }, + { CCI_REG8(0x3820), 0x88 }, + { CCI_REG8(0x3821), 0x00 }, + { CCI_REG8(0x3822), 0x12 }, + { CCI_REG8(0x3823), 0x08 }, + { CCI_REG8(0x3824), 0x00 }, + { CCI_REG8(0x3825), 0x20 }, + { CCI_REG8(0x3826), 0x00 }, + { CCI_REG8(0x3827), 0x08 }, + { CCI_REG8(0x3829), 0x03 }, + { CCI_REG8(0x382a), 0x00 }, + { CCI_REG8(0x382b), 0x00 }, + { CCI_REG8(0x3832), 0x08 }, + { CCI_REG8(0x3838), 0x00 }, + { CCI_REG8(0x3839), 0x00 }, + { CCI_REG8(0x383a), 0x00 }, + { CCI_REG8(0x383b), 0x00 }, + { CCI_REG8(0x383d), 0x01 }, + { CCI_REG8(0x383e), 0x00 }, + { CCI_REG8(0x383f), 0x00 }, + { CCI_REG8(0x3843), 0x00 }, + { CCI_REG8(0x3880), 0x16 }, + { CCI_REG8(0x3881), 0x00 }, + { CCI_REG8(0x3882), 0x08 }, + { CCI_REG8(0x389a), 0x00 }, + { CCI_REG8(0x389b), 0x00 }, + { CCI_REG8(0x38a2), 0x02 }, + { CCI_REG8(0x38a3), 0x02 }, + { CCI_REG8(0x38a4), 0x02 }, + { CCI_REG8(0x38a5), 0x02 }, + { CCI_REG8(0x38a7), 0x04 }, + { CCI_REG8(0x38b8), 0x02 }, + { CCI_REG8(0x3c80), 0x3e }, + { CCI_REG8(0x3c86), 0x01 }, + { CCI_REG8(0x3c87), 0x02 }, + { CCI_REG8(0x389c), 0x00 }, + { CCI_REG8(0x3ca2), 0x0c }, + { CCI_REG8(0x3d85), 0x1b }, + { CCI_REG8(0x3d8c), 0x01 }, + { CCI_REG8(0x3d8d), 0xe2 }, + { CCI_REG8(0x3f00), 0xcb }, + { CCI_REG8(0x3f03), 0x08 }, + { CCI_REG8(0x3f9e), 0x07 }, + { CCI_REG8(0x3f9f), 0x04 }, + { CCI_REG8(0x4000), 0xf3 }, + { CCI_REG8(0x4002), 0x00 }, + { CCI_REG8(0x4003), 0x40 }, + { CCI_REG8(0x4008), 0x02 }, + { CCI_REG8(0x4009), 0x0d }, + { CCI_REG8(0x400a), 0x01 }, + { CCI_REG8(0x400b), 0x00 }, + { CCI_REG8(0x4040), 0x00 }, + { CCI_REG8(0x4041), 0x07 }, + { CCI_REG8(0x4090), 0x14 }, + { CCI_REG8(0x40b0), 0x01 }, + { CCI_REG8(0x40b1), 0x01 }, + { CCI_REG8(0x40b2), 0x30 }, + { CCI_REG8(0x40b3), 0x04 }, + { CCI_REG8(0x40b4), 0xe8 }, + { CCI_REG8(0x40b5), 0x01 }, + { CCI_REG8(0x40b7), 0x07 }, + { CCI_REG8(0x40b8), 0xff }, + { CCI_REG8(0x40b9), 0x00 }, + { CCI_REG8(0x40ba), 0x00 }, + { CCI_REG8(0x4300), 0xff }, + { CCI_REG8(0x4301), 0x00 }, + { CCI_REG8(0x4302), 0x0f }, + { CCI_REG8(0x4303), 0x20 }, + { CCI_REG8(0x4304), 0x20 }, + { CCI_REG8(0x4305), 0x83 }, + { CCI_REG8(0x4306), 0x21 }, + { CCI_REG8(0x430d), 0x00 }, + { CCI_REG8(0x4505), 0xc4 }, + { CCI_REG8(0x4506), 0x00 }, + { CCI_REG8(0x4507), 0x60 }, + { CCI_REG8(0x4803), 0x00 }, + { CCI_REG8(0x4809), 0x8e }, + { CCI_REG8(0x480e), 0x00 }, + { CCI_REG8(0x4813), 0x00 }, + { CCI_REG8(0x4814), 0x2a }, + { CCI_REG8(0x481b), 0x40 }, + { CCI_REG8(0x481f), 0x30 }, + { CCI_REG8(0x4825), 0x34 }, + { CCI_REG8(0x4829), 0x64 }, + { CCI_REG8(0x4837), 0x12 }, + { CCI_REG8(0x484b), 0x07 }, + { CCI_REG8(0x4883), 0x36 }, + { CCI_REG8(0x4885), 0x03 }, + { CCI_REG8(0x488b), 0x00 }, + { CCI_REG8(0x4d06), 0x01 }, + { CCI_REG8(0x4e00), 0x2a }, + { CCI_REG8(0x4e0d), 0x00 }, + { CCI_REG8(0x5000), 0xf9 }, + { CCI_REG8(0x5001), 0x09 }, + { CCI_REG8(0x5004), 0x00 }, + { CCI_REG8(0x5005), 0x0e }, + { CCI_REG8(0x5036), 0x00 }, + { CCI_REG8(0x5080), 0x04 }, + { CCI_REG8(0x5082), 0x00 }, + { CCI_REG8(0x5180), 0x00 }, + { CCI_REG8(0x5181), 0x10 }, + { CCI_REG8(0x5182), 0x01 }, + { CCI_REG8(0x5183), 0xdf }, + { CCI_REG8(0x5184), 0x02 }, + { CCI_REG8(0x5185), 0x6c }, + { CCI_REG8(0x5189), 0x48 }, + { CCI_REG8(0x520a), 0x03 }, + { CCI_REG8(0x520b), 0x0f }, + { CCI_REG8(0x520c), 0x3f }, + { CCI_REG8(0x580b), 0x03 }, + { CCI_REG8(0x580d), 0x00 }, + { CCI_REG8(0x580f), 0x00 }, + { CCI_REG8(0x5820), 0x00 }, + { CCI_REG8(0x5821), 0x00 }, + { CCI_REG8(0x3222), 0x03 }, + { CCI_REG8(0x3208), 0x06 }, + { CCI_REG8(0x3701), 0x1d }, + { CCI_REG8(0x37ab), 0x01 }, + { CCI_REG8(0x3790), 0x21 }, + { CCI_REG8(0x38be), 0x00 }, + { CCI_REG8(0x3791), 0x5a }, + { CCI_REG8(0x37bf), 0x1c }, + { CCI_REG8(0x3610), 0x37 }, + { CCI_REG8(0x3208), 0x16 }, + { CCI_REG8(0x3208), 0x07 }, + { CCI_REG8(0x3701), 0x1d }, + { CCI_REG8(0x37ab), 0x0e }, + { CCI_REG8(0x3790), 0x21 }, + { CCI_REG8(0x38be), 0x00 }, + { CCI_REG8(0x3791), 0x5a }, + { CCI_REG8(0x37bf), 0x0a }, + { CCI_REG8(0x3610), 0x87 }, + { CCI_REG8(0x3208), 0x17 }, + { CCI_REG8(0x3208), 0x08 }, + { CCI_REG8(0x3701), 0x1d }, + { CCI_REG8(0x37ab), 0x0e }, + { CCI_REG8(0x3790), 0x21 }, + { CCI_REG8(0x38be), 0x00 }, + { CCI_REG8(0x3791), 0x5a }, + { CCI_REG8(0x37bf), 0x0a }, + { CCI_REG8(0x3610), 0x87 }, + { CCI_REG8(0x3208), 0x18 }, + { CCI_REG8(0x3208), 0x09 }, + { CCI_REG8(0x3701), 0x1d }, + { CCI_REG8(0x37ab), 0x0e }, + { CCI_REG8(0x3790), 0x28 }, + { CCI_REG8(0x38be), 0x00 }, + { CCI_REG8(0x3791), 0x63 }, + { CCI_REG8(0x37bf), 0x0a }, + { CCI_REG8(0x3610), 0x87 }, + { CCI_REG8(0x3208), 0x19 }, +}; + +struct os05b10 { + struct device *dev; + struct regmap *cci; + struct v4l2_subdev sd; + struct media_pad pad; + struct clk *xclk; + struct i2c_client *client; + struct gpio_desc *reset_gpio; + struct regulator_bulk_data supplies[ARRAY_SIZE(os05b10_supply_name)]; + + /* V4L2 Controls */ + struct v4l2_ctrl_handler handler; + struct v4l2_ctrl *link_freq; + struct v4l2_ctrl *hblank; + struct v4l2_ctrl *vblank; + struct v4l2_ctrl *gain; + struct v4l2_ctrl *exposure; +}; + +struct os05b10_mode { + u32 width; + u32 height; + u32 vts; + u32 hts; + u32 exp; +}; + +static const struct os05b10_mode supported_modes_10bit[] =3D { + { + .width =3D 2592, + .height =3D 1944, + .vts =3D 2006, + .hts =3D 2616, + .exp =3D 1944, + }, +}; + +static const s64 link_frequencies[] =3D { + OS05B10_LINK_FREQ_600MHZ, +}; + +static const u32 os05b10_mbus_codes[] =3D { + MEDIA_BUS_FMT_SBGGR10_1X10, +}; + +static inline struct os05b10 *to_os05b10(struct v4l2_subdev *sd) +{ + return container_of_const(sd, struct os05b10, sd); +}; + +static int os05b10_set_ctrl(struct v4l2_ctrl *ctrl) +{ + struct os05b10 *os05b10 =3D container_of_const(ctrl->handler, + struct os05b10, handler); + struct v4l2_subdev_state *state; + struct v4l2_mbus_framefmt *fmt; + int vmax, ret; + + state =3D v4l2_subdev_get_locked_active_state(&os05b10->sd); + fmt =3D v4l2_subdev_state_get_format(state, 0); + + if (ctrl->id =3D=3D V4L2_CID_VBLANK) { + /* Honour the VBLANK limits when setting exposure. */ + s64 max =3D fmt->height + ctrl->val - OS05B10_EXPOSURE_MARGIN; + + ret =3D __v4l2_ctrl_modify_range(os05b10->exposure, + os05b10->exposure->minimum, max, + os05b10->exposure->step, + os05b10->exposure->default_value); + + if (ret) + return ret; + } + + if (pm_runtime_get_if_in_use(os05b10->dev) =3D=3D 0) + return 0; + + switch (ctrl->id) { + case V4L2_CID_VBLANK: + vmax =3D fmt->height + ctrl->val; + ret =3D cci_write(os05b10->cci, OS05B10_REG_VTS, vmax, NULL); + break; + case V4L2_CID_ANALOGUE_GAIN: + ret =3D cci_write(os05b10->cci, OS05B10_REG_ANALOG_GAIN, + ctrl->val, NULL); + break; + case V4L2_CID_EXPOSURE: + ret =3D cci_write(os05b10->cci, OS05B10_REG_EXPOSURE, + ctrl->val, NULL); + break; + default: + ret =3D -EINVAL; + break; + } + + pm_runtime_put(os05b10->dev); + + return ret; +} + +static int os05b10_enum_mbus_code(struct v4l2_subdev *sd, + struct v4l2_subdev_state *sd_state, + struct v4l2_subdev_mbus_code_enum *code) +{ + if (code->index >=3D ARRAY_SIZE(os05b10_mbus_codes)) + return -EINVAL; + + code->code =3D os05b10_mbus_codes[code->index]; + + return 0; +} + +static int os05b10_set_framing_limits(struct os05b10 *os05b10, + const struct os05b10_mode *mode) +{ + u32 hblank, vblank, vblank_max, max_exp; + int ret; + + hblank =3D mode->hts - mode->width; + ret =3D __v4l2_ctrl_modify_range(os05b10->hblank, hblank, hblank, 1, + hblank); + if (ret) + return ret; + + vblank =3D mode->vts - mode->height; + vblank_max =3D OS05B10_VTS_MAX - mode->height; + ret =3D __v4l2_ctrl_modify_range(os05b10->vblank, 0, vblank_max, 1, + vblank); + if (ret) + return ret; + + max_exp =3D mode->vts - OS05B10_EXPOSURE_MARGIN; + return __v4l2_ctrl_modify_range(os05b10->exposure, + OS05B10_EXPOSURE_MIN, max_exp, + OS05B10_EXPOSURE_STEP, mode->exp); +} + +static int os05b10_set_pad_format(struct v4l2_subdev *sd, + struct v4l2_subdev_state *sd_state, + struct v4l2_subdev_format *fmt) +{ + const struct os05b10_mode *mode =3D &supported_modes_10bit[0]; + struct os05b10 *os05b10 =3D to_os05b10(sd); + struct v4l2_mbus_framefmt *format; + int ret; + + fmt->format.width =3D mode->width; + fmt->format.height =3D mode->height; + fmt->format.field =3D V4L2_FIELD_NONE; + fmt->format.colorspace =3D V4L2_COLORSPACE_RAW; + fmt->format.quantization =3D V4L2_QUANTIZATION_FULL_RANGE; + fmt->format.xfer_func =3D V4L2_XFER_FUNC_NONE; + + format =3D v4l2_subdev_state_get_format(sd_state, 0); + + if (fmt->which =3D=3D V4L2_SUBDEV_FORMAT_ACTIVE) { + ret =3D os05b10_set_framing_limits(os05b10, mode); + if (ret) + return ret; + } + + *format =3D fmt->format; + + return 0; +} + +static int os05b10_get_selection(struct v4l2_subdev *sd, + struct v4l2_subdev_state *sd_state, + struct v4l2_subdev_selection *sel) +{ + switch (sel->target) { + case V4L2_SEL_TGT_NATIVE_SIZE: + case V4L2_SEL_TGT_CROP_BOUNDS: + sel->r =3D os05b10_native_area; + return 0; + case V4L2_SEL_TGT_CROP: + case V4L2_SEL_TGT_CROP_DEFAULT: + sel->r =3D os05b10_active_area; + return 0; + default: + return -EINVAL; + } +} + +static int os05b10_enum_frame_size(struct v4l2_subdev *sd, + struct v4l2_subdev_state *sd_state, + struct v4l2_subdev_frame_size_enum *fse) +{ + if (fse->index >=3D ARRAY_SIZE(supported_modes_10bit)) + return -EINVAL; + + fse->min_width =3D supported_modes_10bit[fse->index].width; + fse->max_width =3D fse->min_width; + fse->min_height =3D supported_modes_10bit[fse->index].height; + fse->max_height =3D fse->min_height; + + return 0; +} + +static int os05b10_enable_streams(struct v4l2_subdev *sd, + struct v4l2_subdev_state *state, + u32 pad, u64 streams_mask) +{ + struct os05b10 *os05b10 =3D to_os05b10(sd); + int ret; + + ret =3D pm_runtime_resume_and_get(os05b10->dev); + if (ret < 0) + return ret; + + /* Write common registers */ + ret =3D cci_multi_reg_write(os05b10->cci, os05b10_common_regs, + ARRAY_SIZE(os05b10_common_regs), NULL); + if (ret) { + dev_err(os05b10->dev, "failed to write common registers\n"); + goto err_rpm_put; + } + + /* Apply customized user controls */ + ret =3D __v4l2_ctrl_handler_setup(os05b10->sd.ctrl_handler); + if (ret) + goto err_rpm_put; + + /* Stream ON */ + ret =3D cci_write(os05b10->cci, OS05B10_REG_CTRL_MODE, + OS05B10_MODE_STREAMING, NULL); + if (ret) + goto err_rpm_put; + + return 0; + +err_rpm_put: + pm_runtime_put(os05b10->dev); + + return ret; +} + +static int os05b10_disable_streams(struct v4l2_subdev *sd, + struct v4l2_subdev_state *state, + u32 pad, u64 streams_mask) +{ + struct os05b10 *os05b10 =3D to_os05b10(sd); + int ret; + + ret =3D cci_write(os05b10->cci, OS05B10_REG_CTRL_MODE, + OS05B10_MODE_STANDBY, NULL); + if (ret) + dev_err(os05b10->dev, "failed to set stream off\n"); + + pm_runtime_put(os05b10->dev); + + return ret; +} + +static int os05b10_init_state(struct v4l2_subdev *sd, + struct v4l2_subdev_state *state) +{ + struct v4l2_mbus_framefmt *format; + const struct os05b10_mode *mode; + + /* Initialize try_fmt */ + format =3D v4l2_subdev_state_get_format(state, 0); + + mode =3D &supported_modes_10bit[0]; + format->code =3D MEDIA_BUS_FMT_SBGGR10_1X10; + + /* Update image pad formate */ + format->width =3D mode->width; + format->height =3D mode->height; + format->field =3D V4L2_FIELD_NONE; + format->colorspace =3D V4L2_COLORSPACE_RAW; + format->quantization =3D V4L2_QUANTIZATION_FULL_RANGE; + format->xfer_func =3D V4L2_XFER_FUNC_NONE; + + return 0; +} + +static const struct v4l2_subdev_video_ops os05b10_video_ops =3D { + .s_stream =3D v4l2_subdev_s_stream_helper, +}; + +static const struct v4l2_subdev_pad_ops os05b10_pad_ops =3D { + .enum_mbus_code =3D os05b10_enum_mbus_code, + .get_fmt =3D v4l2_subdev_get_fmt, + .set_fmt =3D os05b10_set_pad_format, + .get_selection =3D os05b10_get_selection, + .enum_frame_size =3D os05b10_enum_frame_size, + .enable_streams =3D os05b10_enable_streams, + .disable_streams =3D os05b10_disable_streams, +}; + +static const struct v4l2_subdev_internal_ops os05b10_internal_ops =3D { + .init_state =3D os05b10_init_state, +}; + +static const struct v4l2_subdev_ops os05b10_subdev_ops =3D { + .video =3D &os05b10_video_ops, + .pad =3D &os05b10_pad_ops, +}; + +static const struct v4l2_ctrl_ops os05b10_ctrl_ops =3D { + .s_ctrl =3D os05b10_set_ctrl, +}; + +static int os05b10_identify_module(struct os05b10 *os05b10) +{ + int ret; + u64 val; + + ret =3D cci_read(os05b10->cci, OS05B10_REG_CHIP_ID, &val, NULL); + if (ret) + return dev_err_probe(os05b10->dev, ret, + "failed to read chip id %x\n", + OS05B10_CHIP_ID); + + if (val !=3D OS05B10_CHIP_ID) + return dev_err_probe(os05b10->dev, -ENODEV, + "chip id mismatch: %x!=3D%llx\n", + OS05B10_CHIP_ID, val); + + return 0; +} + +static int os05b10_power_on(struct device *dev) +{ + struct v4l2_subdev *sd =3D dev_get_drvdata(dev); + struct os05b10 *os05b10 =3D to_os05b10(sd); + unsigned long delay_us; + int ret; + + /* Enable power rails */ + ret =3D regulator_bulk_enable(ARRAY_SIZE(os05b10_supply_name), + os05b10->supplies); + if (ret) { + dev_err(os05b10->dev, "failed to enable regulators\n"); + return ret; + } + + /* Enable xclk */ + ret =3D clk_prepare_enable(os05b10->xclk); + if (ret) { + dev_err(os05b10->dev, "failed to enable clock\n"); + goto err_regulator_off; + } + + gpiod_set_value_cansleep(os05b10->reset_gpio, 0); + + /* Delay T1 */ + fsleep(5 * USEC_PER_MSEC); + + /* Delay T2 (8192 cycles before SCCB/I2C access) */ + delay_us =3D DIV_ROUND_UP(8192, OS05B10_XCLK_FREQ / 1000 / 1000); + usleep_range(delay_us, delay_us * 2); + + return 0; + +err_regulator_off: + regulator_bulk_disable(ARRAY_SIZE(os05b10_supply_name), + os05b10->supplies); + + return ret; +} + +static int os05b10_power_off(struct device *dev) +{ + struct v4l2_subdev *sd =3D dev_get_drvdata(dev); + struct os05b10 *os05b10 =3D to_os05b10(sd); + + gpiod_set_value_cansleep(os05b10->reset_gpio, 1); + + regulator_bulk_disable(ARRAY_SIZE(os05b10_supply_name), + os05b10->supplies); + clk_disable_unprepare(os05b10->xclk); + + return 0; +} + +static int os05b10_parse_endpoint(struct os05b10 *os05b10) +{ + struct v4l2_fwnode_endpoint bus_cfg =3D { + .bus_type =3D V4L2_MBUS_CSI2_DPHY + }; + unsigned long link_freq_bitmap; + struct fwnode_handle *ep; + int ret; + + ep =3D fwnode_graph_get_endpoint_by_id(dev_fwnode(os05b10->dev), 0, 0, 0); + if (!ep) { + dev_err(os05b10->dev, "Failed to get next endpoint\n"); + return -EINVAL; + } + + ret =3D v4l2_fwnode_endpoint_alloc_parse(ep, &bus_cfg); + fwnode_handle_put(ep); + if (ret) + return ret; + + if (bus_cfg.bus.mipi_csi2.num_data_lanes !=3D 4) { + ret =3D dev_err_probe(os05b10->dev, -EINVAL, + "only 4 data lanes are supported\n"); + goto error_out; + } + + ret =3D v4l2_link_freq_to_bitmap(os05b10->dev, bus_cfg.link_frequencies, + bus_cfg.nr_of_link_frequencies, + link_frequencies, + ARRAY_SIZE(link_frequencies), + &link_freq_bitmap); + + if (ret) + dev_err(os05b10->dev, "only 600MHz frequency is available\n"); + +error_out: + v4l2_fwnode_endpoint_free(&bus_cfg); + + return ret; +} + +static int os05b10_init_controls(struct os05b10 *os05b10) +{ + const struct os05b10_mode *mode =3D &supported_modes_10bit[0]; + struct v4l2_fwnode_device_properties props; + struct v4l2_ctrl_handler *ctrl_hdlr; + u64 hblank_def, vblank_def, exp_max; + int ret; + + ctrl_hdlr =3D &os05b10->handler; + v4l2_ctrl_handler_init(ctrl_hdlr, 8); + + v4l2_ctrl_new_std(ctrl_hdlr, &os05b10_ctrl_ops, V4L2_CID_PIXEL_RATE, + OS05B10_PIXEL_RATE, OS05B10_PIXEL_RATE, 1, + OS05B10_PIXEL_RATE); + + os05b10->link_freq =3D v4l2_ctrl_new_int_menu(ctrl_hdlr, &os05b10_ctrl_op= s, + V4L2_CID_LINK_FREQ, + ARRAY_SIZE(link_frequencies) - 1, + 0, link_frequencies); + + if (os05b10->link_freq) + os05b10->link_freq->flags |=3D V4L2_CTRL_FLAG_READ_ONLY; + + hblank_def =3D mode->hts - mode->width; + os05b10->hblank =3D v4l2_ctrl_new_std(ctrl_hdlr, NULL, V4L2_CID_HBLANK, + hblank_def, hblank_def, + 1, hblank_def); + if (os05b10->hblank) + os05b10->hblank->flags |=3D V4L2_CTRL_FLAG_READ_ONLY; + + vblank_def =3D mode->vts - mode->height; + os05b10->vblank =3D v4l2_ctrl_new_std(ctrl_hdlr, &os05b10_ctrl_ops, + V4L2_CID_VBLANK, vblank_def, + OS05B10_VTS_MAX - mode->height, + 1, vblank_def); + + exp_max =3D mode->vts - OS05B10_EXPOSURE_MARGIN; + os05b10->exposure =3D v4l2_ctrl_new_std(ctrl_hdlr, &os05b10_ctrl_ops, + V4L2_CID_EXPOSURE, + OS05B10_EXPOSURE_MIN, + exp_max, OS05B10_EXPOSURE_STEP, + mode->exp); + + os05b10->gain =3D v4l2_ctrl_new_std(ctrl_hdlr, &os05b10_ctrl_ops, + V4L2_CID_ANALOGUE_GAIN, + OS05B10_ANALOG_GAIN_MIN, + OS05B10_ANALOG_GAIN_MAX, + OS05B10_ANALOG_GAIN_STEP, + OS05B10_ANALOG_GAIN_DEFAULT); + + if (ctrl_hdlr->error) { + ret =3D ctrl_hdlr->error; + dev_err(os05b10->dev, "control init failed (%d)\n", ret); + goto error; + } + + ret =3D v4l2_fwnode_device_parse(os05b10->dev, &props); + if (ret) + goto error; + + ret =3D v4l2_ctrl_new_fwnode_properties(ctrl_hdlr, &os05b10_ctrl_ops, + &props); + if (ret) + goto error; + + os05b10->sd.ctrl_handler =3D ctrl_hdlr; + + return 0; + +error: + v4l2_ctrl_handler_free(ctrl_hdlr); + + return ret; +} + +static int os05b10_probe(struct i2c_client *client) +{ + struct os05b10 *os05b10; + unsigned int xclk_freq; + unsigned int i; + int ret; + + os05b10 =3D devm_kzalloc(&client->dev, sizeof(*os05b10), GFP_KERNEL); + if (!os05b10) + return -ENOMEM; + + os05b10->client =3D client; + os05b10->dev =3D &client->dev; + + v4l2_i2c_subdev_init(&os05b10->sd, client, &os05b10_subdev_ops); + + os05b10->cci =3D devm_cci_regmap_init_i2c(client, 16); + if (IS_ERR(os05b10->cci)) + return dev_err_probe(os05b10->dev, PTR_ERR(os05b10->cci), + "failed to initialize CCI\n"); + + os05b10->xclk =3D devm_v4l2_sensor_clk_get(os05b10->dev, NULL); + if (IS_ERR(os05b10->xclk)) + return dev_err_probe(os05b10->dev, PTR_ERR(os05b10->xclk), + "failed to get xclk\n"); + + xclk_freq =3D clk_get_rate(os05b10->xclk); + if (xclk_freq !=3D OS05B10_XCLK_FREQ) + return dev_err_probe(os05b10->dev, -EINVAL, + "xclk frequency not supported: %d Hz\n", + xclk_freq); + + for (i =3D 0; i < ARRAY_SIZE(os05b10_supply_name); i++) + os05b10->supplies[i].supply =3D os05b10_supply_name[i]; + + ret =3D devm_regulator_bulk_get(os05b10->dev, + ARRAY_SIZE(os05b10_supply_name), + os05b10->supplies); + if (ret) + return dev_err_probe(os05b10->dev, ret, + "failed to get regulators\n"); + + ret =3D os05b10_parse_endpoint(os05b10); + if (ret) + return dev_err_probe(os05b10->dev, ret, + "failed to parse endpoint configuration\n"); + + os05b10->reset_gpio =3D devm_gpiod_get_optional(&client->dev, "reset", + GPIOD_OUT_LOW); + if (IS_ERR(os05b10->reset_gpio)) + return dev_err_probe(os05b10->dev, PTR_ERR(os05b10->reset_gpio), + "failed to get reset GPIO\n"); + + ret =3D os05b10_power_on(os05b10->dev); + if (ret) + return ret; + + ret =3D os05b10_identify_module(os05b10); + if (ret) + goto error_power_off; + + /* This needs the pm runtime to be registered. */ + ret =3D os05b10_init_controls(os05b10); + if (ret) + goto error_power_off; + + /* Initialize subdev */ + os05b10->sd.flags |=3D V4L2_SUBDEV_FL_HAS_DEVNODE; + os05b10->sd.entity.function =3D MEDIA_ENT_F_CAM_SENSOR; + os05b10->sd.internal_ops =3D &os05b10_internal_ops; + os05b10->pad.flags =3D MEDIA_PAD_FL_SOURCE; + + ret =3D media_entity_pads_init(&os05b10->sd.entity, 1, &os05b10->pad); + if (ret) { + dev_err_probe(os05b10->dev, ret, + "failed to init entity pads\n"); + goto error_handler_free; + } + + os05b10->sd.state_lock =3D os05b10->handler.lock; + ret =3D v4l2_subdev_init_finalize(&os05b10->sd); + if (ret < 0) { + dev_err_probe(os05b10->dev, ret, "subdev init error\n"); + goto error_media_entity; + } + + pm_runtime_set_active(os05b10->dev); + pm_runtime_enable(os05b10->dev); + + ret =3D v4l2_async_register_subdev_sensor(&os05b10->sd); + if (ret < 0) { + dev_err_probe(os05b10->dev, ret, + "failed to register os05b10 sub-device\n"); + goto error_subdev_cleanup; + } + + pm_runtime_idle(os05b10->dev); + + return 0; + +error_subdev_cleanup: + v4l2_subdev_cleanup(&os05b10->sd); + pm_runtime_disable(os05b10->dev); + pm_runtime_set_suspended(os05b10->dev); + +error_media_entity: + media_entity_cleanup(&os05b10->sd.entity); + +error_handler_free: + v4l2_ctrl_handler_free(os05b10->sd.ctrl_handler); + +error_power_off: + os05b10_power_off(os05b10->dev); + + return ret; +} + +static void os05b10_remove(struct i2c_client *client) +{ + struct v4l2_subdev *sd =3D i2c_get_clientdata(client); + struct os05b10 *os05b10 =3D to_os05b10(sd); + + v4l2_async_unregister_subdev(sd); + v4l2_subdev_cleanup(&os05b10->sd); + media_entity_cleanup(&sd->entity); + v4l2_ctrl_handler_free(os05b10->sd.ctrl_handler); + + pm_runtime_disable(&client->dev); + if (!pm_runtime_status_suspended(&client->dev)) { + os05b10_power_off(&client->dev); + pm_runtime_set_suspended(&client->dev); + } +} + +static DEFINE_RUNTIME_DEV_PM_OPS(os05b10_pm_ops, os05b10_power_off, + os05b10_power_on, NULL); + +static const struct of_device_id os05b10_id[] =3D { + { .compatible =3D "ovti,os05b10" }, + { /* sentinel */ }, +}; + +MODULE_DEVICE_TABLE(of, os05b10_id); + +static struct i2c_driver os05b10_driver =3D { + .driver =3D { + .name =3D "os05b10", + .pm =3D pm_ptr(&os05b10_pm_ops), + .of_match_table =3D os05b10_id, + }, + .probe =3D os05b10_probe, + .remove =3D os05b10_remove, +}; + +module_i2c_driver(os05b10_driver); + +MODULE_DESCRIPTION("OS05B10 Camera Sensor Driver"); +MODULE_AUTHOR("Himanshu Bhavani "); +MODULE_AUTHOR("Elgin Perumbilly "); +MODULE_LICENSE("GPL"); -- 2.34.1