From nobody Mon Jun 8 17:39:44 2026 Received: from DM1PR04CU001.outbound.protection.outlook.com (mail-centralusazon11010011.outbound.protection.outlook.com [52.101.61.11]) (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 D3BB34266BA; Wed, 27 May 2026 17:55:53 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.61.11 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904555; cv=fail; b=S/8/pKuk3VRRH6tMClla51koDQPFc/9JDOmBR1GCH/LMHot+VHXmiQO5guDI04bIQf8d7UWkol0C7ndu7tEsvKOYFjZWyS5Futwtv+/J6NCsJFSgyNh2wulrbe/HwiYgd+NTRp+c33X8TAOnPUqYuxdCyS1f3NdloABNkc3Drgo= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904555; c=relaxed/simple; bh=DPx2geiC+e6vKCIASN3DloUYdzJWZ1kgBrBghQxSqT0=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=sxv+Qw5XA9OH2atMWZue2IqIXnnOArx5Sxir3k8oK4SiudhLTSpWVD8OOOCbCsI2KFGV7YjDFL9MfdiZeU+92LyfdVoHITWzrqWZ5oTbU/NmMuMx754msrWTQ66YGT62S8cGMOOEucIFdn1h4kILz1mewbTmcFc+GXsWghdsjbA= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=KLb4yZbM; arc=fail smtp.client-ip=52.101.61.11 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="KLb4yZbM" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=uAExmHRN+vB469Yra93xe2ryHXR0+V2na422NS7DVThi0Iwf0AmFnSwuF3BFbVo9JymLdHV0a7Y+jGmCyyp36/hZQVFzaFU42tCmH7fvdQePu33P9f6M5Guotpn6cIQ9Qz9CxkrZ/VyHtPpd8LeAIAZMQ0z0qGqMEma2MNFYpPwkApGKgzyataIkZMhRj9di6UTYiRdyIxQ43UdQehnPpj1om36Zk0WaLs5X+WCp71lNV0qx0Dl3IAP3MGlAM/dVP94XpbEQ6An5IffFHcDi5435vjX47Wp097DgZU3d83RL1LmX+vw6NwxM0OH9rm08WkregLF/gs0SrDtwN6xtVQ== 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=Lufe1WLqLVvDMCaLJGFT6z969LKNNBZnGosNUej+SZg=; b=R2wtQIP2igbf6yKtkm8CHY0QFitOQzktsSO93chuRiux4Mi1oQ8+9n6ZQqHNesmZJ2fT80fMD3WJ41mugJCdDe4i6NaUytYN8DtwSYpFis7rBvuXsyEs9vUJSM0/vDHoF6nahMtWUbWIYElckBJr3Ab6EW6Ol6xZPJmSZfz7PAvNDsWdqluoqQKKjhw3YEuvsfkoa94Qf+kBOO2MSf7Zlr6cX1Quj68J48eiudczwQ8RdjM2sx3aTmCUlfkaBDeybxAdmSeQfuPV93m7a1r9RmRUBiC6nDtTN71r3G7ni33Svmrv1FMtLL5DOC6ZjIRFFJ71rGd2U1IWfkD6+YKZPQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=Lufe1WLqLVvDMCaLJGFT6z969LKNNBZnGosNUej+SZg=; b=KLb4yZbMJ3FUZ8jOSNDkC0YVvFy9O1cP+VdVFmSmFXtJEoUAJQH/DF5tIel6Li4clapM9kW9mtlaUaTHxta/aZUEKiToo89KNaFpuPKpk7eeG0Jg8ZdJpz0xWH6wlQQz8/0v3oQtOMYbi/ONzzuOEWNba//0ZBsznGAhXasZlV8= Received: from MW4PR03CA0202.namprd03.prod.outlook.com (2603:10b6:303:b8::27) by CH3PR10MB7234.namprd10.prod.outlook.com (2603:10b6:610:128::13) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.12; Wed, 27 May 2026 17:55:50 +0000 Received: from CO1PEPF00012E61.namprd05.prod.outlook.com (2603:10b6:303:b8:cafe::44) by MW4PR03CA0202.outlook.office365.com (2603:10b6:303:b8::27) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:55:49 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E61.mail.protection.outlook.com (10.167.249.70) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:55:48 +0000 Received: from DFLE211.ent.ti.com (10.64.6.69) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:44 -0500 Received: from DFLE215.ent.ti.com (10.64.6.73) by DFLE211.ent.ti.com (10.64.6.69) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:44 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE215.ent.ti.com (10.64.6.73) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:55:44 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpd4052476; Wed, 27 May 2026 12:55:39 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 01/13] spi: dt-bindings: allow spi-max-frequency to specify a frequency pair Date: Wed, 27 May 2026 23:25:15 +0530 Message-ID: <20260527175527.2247679-2-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E61:EE_|CH3PR10MB7234:EE_ X-MS-Office365-Filtering-Correlation-Id: 430e7a21-134b-4f83-2caf-08debc192f38 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|376014|7416014|1800799024|36860700016|82310400026|18002099003|22082099003|921020|3023799007|5023799004|56012099006|6133799003; X-Microsoft-Antispam-Message-Info: GyqfRfr0YGb5D4QsCEVjsQVoRRrqvJqY9xw/utFRn5PQMtJW2iE+Gd8sEEpk9JX3H5AjayRdWEuVDqm6KO4Sqiisv0RRkSxLypfl4r6llGh/l8xlzYwgXMRGJ+/Gl2W3CaTSFkVpLmEEmrXJhhclwbK5PgXWtT1S3VerBwDh4+EP3+/JUKYpRy+ahzI5bPetElhtn2DD9IPSaJ6g83nZtclV1NYXB754X/bME9rRlTGaLcBtZAbU6GKVtCjoNxB/+auuutAVk0BAL22xhwh0FzOTcytMH6uICjivqAAeycfp5y3p0VF0hQyMo9/r9sDUtxfngbLNACWn7NteRt4QR1IldCYorqQXj/uPN6lVVflWzXnSnXZW+v9ahlcGzs8jSxppsA768bgojE0TrTLcLRh4i1HpHVK4h0wz1DuKYl1Zb1wJI96QCXaxu0i6FcNb3GINJksm65/FH0dHLXW9VDy1YSOHYD5D3QtEV/42fXBwhVeIEHdZA72tmPffSAvSfVKMi0kexfeneCBtoQQ31mJMtSoTmHe8VL1uueds3WKdfdsEEMsRftCwN+NtQTXR2hoQvu8OwgkWuJR602bWMuWWLxt1RQaVGoIxgyQvTfENpww/xiJ7DrvT4PgFsNC9osK2AY2RGUoHFMeeXBDjEPlmZFaYoBGielwahHMDi3pPYBstGQL4wA44EqY7Uqg/OiYW9PO8R8EvhZR7AKClDT/a7gyO6t7POIne5HzYgIQJjy+ZIijFeyZPxi2Rczt3+3KMAGRve/nfuJ5Ya9v61Q== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(376014)(7416014)(1800799024)(36860700016)(82310400026)(18002099003)(22082099003)(921020)(3023799007)(5023799004)(56012099006)(6133799003);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: S/wKHs1CPWJdo2TIDizPqL36hdyVENCUwH6gfcESY4eOOxG7Q9EYo52VBpOPJS8Qn400Hdu27OCRh52RX5F+96vykvSaXYk6IGiZtmJl0zMc3ewXRalh7mpv/qPEM1KUsRax9Yfzl1pv8/iPA2C+IqNfGJhXOqzJCiw95Ktg+EHLbhh/rbSk8Aa5X/NcLaJx8IUuChCeNrcTNZMNMo65JL2ZcUHK/TLFc7iYT6G2QA87qTNTTZDzFBj4HaaSTmEJBQU62mYJHi5DBfBvxtv6pHm2Gz+BdeWa6Akierj1oC2W+kvpJr3P2g5rRpYe2uXe78tcqtS7jKY36RMmCADBFH4r4B/MyFEqlnplcwGZfSngI7mY9OL/Q9kKSL5D7WX/GLqnBMHZ9EYiZNH0tLQxwjtg+rwzCEoc/poqFiFXUOcpLPYkCn+rgnzR5jH4Io4Q X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:55:48.4338 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 430e7a21-134b-4f83-2caf-08debc192f38 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E61.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: CH3PR10MB7234 Content-Type: text/plain; charset="utf-8" Some SPI controllers support high-speed operating modes that require controller-side configuration before the device can be driven at its rated maximum frequency. In these cases two frequencies are relevant: a conservative speed usable without any such configuration, and the maximum speed achievable once the controller is set up accordingly. The existing spi-max-frequency property accepts only a single u32, which cannot express this distinction. Extend it to accept either a single value (retaining full backward compatibility) or a two-element array [base-frequency, max-frequency], where base-frequency is the conservative operating speed and max-frequency is the highest speed the device supports after controller-side configuration. Signed-off-by: Santhosh Kumar K Reviewed-by: Miquel Raynal --- .../devicetree/bindings/spi/spi-peripheral-props.yaml | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/Documentation/devicetree/bindings/spi/spi-peripheral-props.yam= l b/Documentation/devicetree/bindings/spi/spi-peripheral-props.yaml index 880a9f624566..c88f6f3a1801 100644 --- a/Documentation/devicetree/bindings/spi/spi-peripheral-props.yaml +++ b/Documentation/devicetree/bindings/spi/spi-peripheral-props.yaml @@ -41,9 +41,15 @@ properties: The device requires the LSB first mode. =20 spi-max-frequency: - $ref: /schemas/types.yaml#/definitions/uint32 + $ref: /schemas/types.yaml#/definitions/uint32-array + minItems: 1 + maxItems: 2 description: - Maximum SPI clocking speed of the device in Hz. + SPI clocking speed of the device in Hz. Either a single maximum + frequency, or two values [base-frequency, max-frequency] where + base-frequency is the conservative speed and max-frequency is the + highest speed the device supports after controller-side configuratio= ns + such as data training. =20 spi-cs-setup-delay-ns: description: --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from BN8PR05CU002.outbound.protection.outlook.com (mail-eastus2azon11011057.outbound.protection.outlook.com [52.101.57.57]) (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 A105043DA4B; Wed, 27 May 2026 17:55:57 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.57.57 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904559; cv=fail; b=VdhB+/Zja6t9cG6xw3hSo2uvvcAEUaFF6jJINo6QCg0a5GMT6ODs6+nnld+W6zYLNqVDjW88LVM8Tc0Ruc1fSUcw0Ge8/yIOYTd9dDyA2ssUXi1mLuY8JTKPI5zz8JJWDY0O9AuleJCbmrgRnjpn9RCu+RCXoEBgrDqKMG2+1GQ= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904559; c=relaxed/simple; bh=bpXjMp76giZmsQeRuJ/WTYb3ZoJT4jNOseQ7aUCvYeM=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=dZ8PkBJevFdqa+rSVkmlfpjTJL7lcESfmcIp8pJHXC3qN3o/3Xh49vAsEGevlqMFhDNPRYD5CLv+4PhitJ0xwFxzRWmPm7je/eUgyKq6TtAkiaWVgxeeXDUor5wSXY3sMpWGdN0BTnI4sxfbyGKBDxwsgvfbd3yHuifrILt71B0= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=wbYgDmHP; arc=fail smtp.client-ip=52.101.57.57 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="wbYgDmHP" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=qE1dS9QWxWnr6MgP7Il/AR6PETcUPuSmZ7nSGkq4fsYy8cK85WTckKyb0Kzf/wffBuGF/baRXry3p1KLrFPVTRscCjoplxahgc8JjdKpvLfhEamDxluIASmHQdegPFqIHQIbW/GIoBudpltr37veDXzXN68XR6ILhsz4Cp3oJ/qOtsPhrDCvAbOiA3dJu1DzmZZTlhLyIvlf10qS9qHjS2ygf9nQBCLWXh5h3xR89xvDykTCXJ9eJdvCySy0X1/Z2fCnety1cg8WES8F/CKTd8lBQGjXqSHmLwAvPSanKQwW44+gfSC/QsekvSfxWbIwVQkjPF1Otxhfrtc2N81mEw== 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=S1fz0pGxnj1ULB6Oi47+VwRRlBZ4WvQIPMf+/fWGCGs=; b=uIDZMqEp68yzLKOyISe/PzlJeJo0ZOwJFX7R2HMhXYt0uW2MKYxbSEfq6vhgGW3vymRNg0AOJ6VfAraNF/fot/2BdTr9i0q1MCVkd/NyGLBtHj5gajBAyIyJW4jAnCa8TMqR2Nb8v67Hhz/9G+WuxgIYZ1HGFKrzCulz6vPZarZ/v8LghfAggH1HCPlVP43KbtCFCGEPI3avrFAPOVL8yaTIwdtsEjakIOVQv270UqEbTcL0bE4cUEtSHxS8viAkaurr7dcBWU5e0otwtlVFZIkvHAmuIHZwS+EcGnDzjuj+6dzMlKHkWIBPq0wnfNrxGlp10VY0vI1u22ABEH+V6g== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=S1fz0pGxnj1ULB6Oi47+VwRRlBZ4WvQIPMf+/fWGCGs=; b=wbYgDmHP31oBe1oMDsb67lOe40X1qdu91vXCESOfNrFgJmPNl9ECgz7/p7qk7ykpD4UzaqqiUfQ/j0zq38LaAcVuU0Fbk/QEaQgY94x2hukf244uNzTUABwa089Bf1Xy5IpArZraNFV0PtrnSJEQ+ueW2jdBPO7XqJMV8WYqV8E= Received: from MW4PR03CA0206.namprd03.prod.outlook.com (2603:10b6:303:b8::31) by EAYPR10MB997925.namprd10.prod.outlook.com (2603:10b6:303:2d2::5) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.13; Wed, 27 May 2026 17:55:55 +0000 Received: from CO1PEPF00012E61.namprd05.prod.outlook.com (2603:10b6:303:b8:cafe::ab) by MW4PR03CA0206.outlook.office365.com (2603:10b6:303:b8::31) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:55:55 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E61.mail.protection.outlook.com (10.167.249.70) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:55:54 +0000 Received: from DFLE214.ent.ti.com (10.64.6.72) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:50 -0500 Received: from DFLE207.ent.ti.com (10.64.6.65) by DFLE214.ent.ti.com (10.64.6.72) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:49 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE207.ent.ti.com (10.64.6.65) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:55:49 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpe4052476; Wed, 27 May 2026 12:55:45 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 02/13] spi: dt-bindings: cdns,qspi-nor: add PHY tuning pattern partition property Date: Wed, 27 May 2026 23:25:16 +0530 Message-ID: <20260527175527.2247679-3-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E61:EE_|EAYPR10MB997925:EE_ X-MS-Office365-Filtering-Correlation-Id: cf2edc95-9842-4bfa-e300-08debc193320 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|36860700016|1800799024|376014|7416014|82310400026|921020|56012099006|18002099003|22082099003|3023799007; X-Microsoft-Antispam-Message-Info: KEsEFi3GGy7/pdMbgbaGuDFORB7t1h64V9EAzo5WXcszPdd4/Clr2PBeGQCH20LxBnCOQCvOMJisb4yuTG+mypErOKYsDq5iyj1eY5HgsScWBlKpyrrxGvu8KKdlgYgW8F0uM5LxEVV7Cv4WM+2Dqo1FmcpQqRiKOzkyhAEwnPHeCeHf8WtUkeSmVuIYYUzUvYsYeqafrbl5UiIMuj5LNyHiYVHKtpSFvRUwivfNJm9BhHq8nnEMX+j3F3gNINraPEAlpM2NPzxsvCfCmw9LCnbVB5+vUbkCLecFbSY3lnQIrvE7eGO7dAxgGiHpJkB6EnKndkZpAzQpvYWLI27E5hRqvTXhjmcxmLc683gOlDEAfHiYGMUonIpaWliY9RdDmpr5JdpBK2IGvFAafokrPnWgKl+Q4UuRKahhavuOki1rF+3FQq7evDg2G9MVKALRf4M8qnkYXiRmAVk7j6iQYgaKeJOhQJzT0pKFNoRfaEY4Ft8fwRkGap0b15mPwoswx+mTZjYDrL8rGsETzE72qyAaPKFHOhdFdMQnR8YHJl3CfmZCT8o+xRCyCJALtFyNLLqWj4nyoHSHI4aiafCTsDCGyEzqHBghHIRWYwoOoLFL+AbnQzG8KD0xm0Rx4+oiqmhM4x4zhO1+/5+2wTPcbI77Bv2BSMnLPbAl2WWHW+cTaigbhIjvJVcLcjsW+8orNco902LsxHiSRkTJSsl1xivDxFASoujZcS5+C2E+BHic13oVuIRJN7WDtR7qukXHSLiseQRyrWy4b2bPIG9JyQ== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(36860700016)(1800799024)(376014)(7416014)(82310400026)(921020)(56012099006)(18002099003)(22082099003)(3023799007);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: U4grYMmWhgih8p4HROpO9X9NS5QDgyXuT6mYuf4CiZ2VlZMUAo/M42SoqnLNcSD6OOYE1ck5PyRfYkQGc17RCTUdRPdMQ8GGPUO5zLGKirrmxIdMiMrhjs2odlIE4V7V3reoWT4uUEeOKRLn29BtO9KNnrsewcCkcibGfs06pOBeYXDFUt/be8Gfcd2O9N5NTft2QRLtAlNKoU+QM1MxcNL89N/6I49jUOHbYWHp2iTk7dXKMRwUgwWVZPe3QgXRPyoLx5bz7xj/st5mSyjz9LGGQKRWLa/SNjzZXUCqIbhak00GxIB7p1D+XN1eCNtd+shrA4UTh7loVj7y3yV22D7DiM9NGzeKTMlu+fjC1ML8lYoiiv4WAUrAMe+8CwCTExH23ENsEIEWg4R5CQR6QY53coB6xpl1ofI0py/aQKbaJ2E4f9GESsz412TePSFh X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:55:54.9812 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: cf2edc95-9842-4bfa-e300-08debc193320 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E61.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: EAYPR10MB997925 Content-Type: text/plain; charset="utf-8" PHY tuning requires a known data pattern to be readable from flash. When no partition is explicitly identified, the controller must search all available partitions to locate the pattern by label, which adds overhead and relies on label naming conventions outside the controller's control. Add cdns,phy-pattern-partition, a phandle property that allows the DT author to directly reference the flash partition holding the PHY tuning pattern. The controller uses this partition during calibration, avoiding the partition search entirely. Signed-off-by: Santhosh Kumar K Reviewed-by: Miquel Raynal --- .../bindings/spi/cdns,qspi-nor-peripheral-props.yaml | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/Documentation/devicetree/bindings/spi/cdns,qspi-nor-peripheral= -props.yaml b/Documentation/devicetree/bindings/spi/cdns,qspi-nor-periphera= l-props.yaml index 510b82c177c0..0ffcdf5b00d0 100644 --- a/Documentation/devicetree/bindings/spi/cdns,qspi-nor-peripheral-props.= yaml +++ b/Documentation/devicetree/bindings/spi/cdns,qspi-nor-peripheral-props.= yaml @@ -39,4 +39,12 @@ properties: Delay in nanoseconds between setting qspi_n_ss_out low and first bit transfer. =20 + cdns,phy-pattern-partition: + $ref: /schemas/types.yaml#/definitions/phandle + description: + Phandle to the flash partition containing the PHY tuning pattern. + When present, the controller uses this partition to locate the + pattern data during PHY tuning instead of searching all partitions + by label. + additionalProperties: true --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from SN4PR2101CU001.outbound.protection.outlook.com (mail-southcentralusazon11012065.outbound.protection.outlook.com [40.93.195.65]) (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 9DA0D436353; Wed, 27 May 2026 17:55:58 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=40.93.195.65 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904560; cv=fail; b=ekaT0Cmk/73pSOJY4gRzuY52QrYVHxtmkiUDr8un7ygHaP7izhzR3C0YFZzO8em3GPWFiRurd+SeWRAlU8xLrqQyqpxDelJbmxnPbRlzrrPrg2V8rS59+kuHHGBbSnaQgWDYAdLEj/hK55besQBDthocloGovtWh3/VvWyiXUjI= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904560; c=relaxed/simple; bh=b1YbOYRWZcx+ySt5u5Y/Zxw3OCTphaVHgtvBlPEoeSk=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=BHkiDw8x2cNrYV4usG5EKnJca5rus2YgOGbKfYxeQd3XGObHECtGcKkm+jYJWWnv6s8gvPCTHXU34exkKpUD35/QupAyRxEvN6mSzeKXBtE9iPh/jFXY5raPDyaBTfv4JvM8ctdMGTGgrhOwJPH6jA8pycd+VNaiy3ItinDdX8o= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=cWgAasdy; arc=fail smtp.client-ip=40.93.195.65 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="cWgAasdy" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=iLgjjbZqmOy07u/E5gVJsL1PscUXjlZTaLt7QqnFpL9BfOmlWoZgl5P3XtvhKmKbXmPdGcg9YacAmBm4mZstje9MJ6dcWLO+NQtjH/ZTqE/WRiAMQBMJqgUjj0n0nLjmX3fj8pLga45YHmAz/CQVGvlP8RsWORLdzWGpvJNO+RHWNMa6w9idLM3BdcORg1sEVUE9qeX21bLdkYHWwPAhTWuqxvkwIgcCicqRCkWd0B6n3Qny2/0VgUyHL3O8fR/Qy8OXRyUVie+CQp6buk/DZJlMBrlcLuCIz+du18GfiQopNJuZSjaeeeVuCpH1QlCKRpMGbM7ZlqBDdl3eAAa6Eg== 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=9VPNAFTfr723ACIvG/rZBUHSYFLm4vjlOPz/Bs1eEP0=; b=SpVS1M2kzMMziFwkou1ZjZJO6ysfEVRLrUoxnUV2jERZd4xi7Q1H1naD+db47ikfB+L+0FExmyq2y9GSrhh5O55VGHOcb9kQFObKEgqK/FVV86Iu3p1NCI1PQah6ObvtReCZHDBcOCQuik6cy0uq9qI1i5jyQho8/RMcssNEv9wCwKVNwC1nKzkjtnnMuvZyXUKYcx6B/vc637Z6E3ayYddgy5BaR52C+FNFHnfC1SAIebVW7MOKrYbuspEFkAKl7CXoUTjcba7WD7hy0nT29dCKspWb2jnympNyScPUlcrvpsqBwaUZ8/uvocCoUIIgHoZz+2oGwtqSUSx6rDO2Og== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.23.194) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=9VPNAFTfr723ACIvG/rZBUHSYFLm4vjlOPz/Bs1eEP0=; b=cWgAasdy6fIjPQiriHHMjKHR0ClEDKJDvADd2Ps3OFW0RVWcTQERzdKcqvfN40TFahJ5fqWzEVG5dgGc772wjs3TlIt6jU0T0OjSqFrX7JQzUyQplQklvOASmCOa748hFE587BEujl6QRHpjZS6n/8BqRZm3FnpK5OMv3aGMv4Y= Received: from DS1P220CA0010.NAMP220.PROD.OUTLOOK.COM (2603:10b6:8:455::16) by IA3PR10MB8662.namprd10.prod.outlook.com (2603:10b6:208:570::22) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.11; Wed, 27 May 2026 17:55:56 +0000 Received: from DM2PEPF00003FC9.namprd04.prod.outlook.com (2603:10b6:8:455:cafe::51) by DS1P220CA0010.outlook.office365.com (2603:10b6:8:455::16) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:55:56 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.23.194) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.23.194 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.23.194; helo=lewvzet200.ext.ti.com; pr=C Received: from lewvzet200.ext.ti.com (198.47.23.194) by DM2PEPF00003FC9.mail.protection.outlook.com (10.167.23.27) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:55:55 +0000 Received: from DLEE214.ent.ti.com (157.170.170.117) by lewvzet200.ext.ti.com (10.4.14.103) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:55 -0500 Received: from DLEE203.ent.ti.com (157.170.170.78) by DLEE214.ent.ti.com (157.170.170.117) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:54 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DLEE203.ent.ti.com (157.170.170.78) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:55:54 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpf4052476; Wed, 27 May 2026 12:55:50 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 03/13] spi: parse two-element spi-max-frequency property Date: Wed, 27 May 2026 23:25:17 +0530 Message-ID: <20260527175527.2247679-4-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: DM2PEPF00003FC9:EE_|IA3PR10MB8662:EE_ X-MS-Office365-Filtering-Correlation-Id: 2c92f709-6edb-4ad4-b7d1-08debc19335a X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|36860700016|82310400026|376014|7416014|1800799024|921020|22082099003|18002099003|3023799007|6133799003|56012099006; X-Microsoft-Antispam-Message-Info: b5n1T3dkIkhfdCH+lWf05BM1AHkd+g6tabB77ys/W+hxMJOYNwnhH2qeNsAmciiq4FD0OZOrOlhWhzSUeLW8SQ9EF4tfGkjdgjJHdHMD1fPwRZC23qKlDVvdRl17diFJ2Yoeyes9fLeiG33TfyKvNzXFR0fszdu0Fj9a7r/ihobmaZ9r4GGxRvNCvkbvrV2bYgTnQlWoFJpqDpO4YhFegPnO8wZmngF/CdZOmsH6tBv8urxsDNoH5l4tdQ3R7Kjx0HUxenUmmCTc//WBCUEQ4JoJfo9XIG4HaroklYZk3LOi+RwIiePAWfCHW27U1C8wVU5/IQquPkAcp25d+YeAt90JA9IkRAmscOy7feTxJwY1x11+JTSDErvBhTUUKrRQhgvMwvWmzxSdv6boOyXw6tdcKJN8L9kiIg6UNygtPPHB3iFRMLw1jUkWVgkc9/bdpiZNGkRUxfSmdrTCvKfbJ+3PyQzmdXEwJ0SlgmwPt8od2HWWz8js1X37WA3ijVnTSF7153cQF3Mwr53IaHwCkUWkzgkuILbBPkv4qP4RWMaFUqSvJLIxkGyLntOR3TWSRgTQ3Jm02jz9lSH4PfTIiIXjmX9Tv5fu1IDoJaKcXFylLtdct31v+ZhQRB85/RaAZnl/j+ArV2/9ipJ9zGeQqzw1YBp/0JpzOT2CoR0019P8f6d/CAfhzEtvM7RSmVIb5YNhMxgsCPC8U8ynbLxwWu915FJvBJtm94Sfrg9bSB3LXseGVZh2ZBzYP65jvdXB6RUZ5M+HN11BLMHAZ+8bCw== X-Forefront-Antispam-Report: CIP:198.47.23.194;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:lewvzet200.ext.ti.com;PTR:InfoDomainNonexistent;CAT:NONE;SFS:(13230040)(36860700016)(82310400026)(376014)(7416014)(1800799024)(921020)(22082099003)(18002099003)(3023799007)(6133799003)(56012099006);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: NMZqpzAe82YzDrqQ9mjm+5LCFpqyD7Wwc20liDxzvHaDtJKnZgY1xU9qeSOdwugMVwi7aQ3hyHftG7Jldifzd2ulAQfY+h+zWLR9xSIUcwNS4eA+AJzg6ZSY8tVljpsLRAg7RgZTO/T50xqgvDeGpU72SJKmMN5pBYwfIAAY0hBNbL2kGmDG8m1Szhf/eNlZpgvoTSlo0UQlc7rBnM+rNiMpfJ4XWHgPhv0VXc20t+PelVIw8X8AQ6O6ydTjz+omPe3urFioaLHnyIe6Ksj0PDXCsIyr5zQs3VdnPIEKq1R8EaDc/fOHKiGFB1uVnpFW68bVMXtK1Yb6Pw3nWuI2FfIvdaLk1PhDpqlpSj2M9IktlDzebwK4CgIOnOV3hVJaQWT2pQp+gEyrcvir6X3p7kuDPjLuDbKyg4tE+SIrLq3bl4Qgt8sKGCOLQq6YWgmL X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:55:55.4018 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 2c92f709-6edb-4ad4-b7d1-08debc19335a X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.23.194];Helo=[lewvzet200.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: DM2PEPF00003FC9.namprd04.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: IA3PR10MB8662 Content-Type: text/plain; charset="utf-8" Some SPI controllers support high-speed operating modes that require controller-side configuration before the device can be driven at its rated maximum. In such cases the device has two relevant speeds: a conservative rate for baseline operation and a maximum rate achievable once the controller is fully configured. Extend struct spi_device with a base_speed_hz field. Update of_spi_parse_dt() to populate base_speed_hz from the first element and max_speed_hz from the second when spi-max-frequency carries two values. A single-element property continues to populate only max_speed_hz, preserving existing behaviour. base_speed_hz is zero when not set. Signed-off-by: Santhosh Kumar K Reviewed-by: Miquel Raynal --- drivers/spi/spi.c | 17 ++++++++++++++--- include/linux/spi/spi.h | 2 ++ 2 files changed, 16 insertions(+), 3 deletions(-) diff --git a/drivers/spi/spi.c b/drivers/spi/spi.c index 76e3563c523f..a1050b1a1d4c 100644 --- a/drivers/spi/spi.c +++ b/drivers/spi/spi.c @@ -2364,7 +2364,7 @@ static int of_spi_parse_dt(struct spi_controller *ctl= r, struct spi_device *spi, struct device_node *nc) { u32 value, cs[SPI_DEVICE_CS_CNT_MAX], map[SPI_DEVICE_DATA_LANE_CNT_MAX]; - int rc, idx, max_num_data_lanes; + int rc, idx, max_num_data_lanes, nfreq; =20 /* Mode (clock phase/polarity/etc.) */ if (of_property_read_bool(nc, "spi-cpha")) @@ -2596,9 +2596,20 @@ static int of_spi_parse_dt(struct spi_controller *ct= lr, struct spi_device *spi, */ spi->cs_index_mask =3D BIT(0); =20 - /* Device speed */ - if (!of_property_read_u32(nc, "spi-max-frequency", &value)) + /* + * Device speed: a single value sets max_speed_hz; two values set + * base_speed_hz (conservative) and max_speed_hz (maximum after + * controller-side configuration). + */ + nfreq =3D of_property_count_u32_elems(nc, "spi-max-frequency"); + if (nfreq =3D=3D 2) { + of_property_read_u32_index(nc, "spi-max-frequency", 0, + &spi->base_speed_hz); + of_property_read_u32_index(nc, "spi-max-frequency", 1, + &spi->max_speed_hz); + } else if (!of_property_read_u32(nc, "spi-max-frequency", &value)) { spi->max_speed_hz =3D value; + } =20 /* Device CS delays */ of_spi_parse_dt_cs_delay(nc, &spi->cs_setup, "spi-cs-setup-delay-ns"); diff --git a/include/linux/spi/spi.h b/include/linux/spi/spi.h index f6ed93eff00b..e4fc8ac1c889 100644 --- a/include/linux/spi/spi.h +++ b/include/linux/spi/spi.h @@ -139,6 +139,7 @@ extern void spi_transfer_cs_change_delay_exec(struct sp= i_message *msg, * @max_speed_hz: Maximum clock rate to be used with this chip * (on this board); may be changed by the device's driver. * The spi_transfer.speed_hz can override this for each transfer. + * @base_speed_hz: Conservative clock rate for the device; zero when not s= et. * @bits_per_word: Data transfers involve one or more words; word sizes * like eight or 12 bits are common. In-memory wordsizes are * powers of two bytes (e.g. 20 bit samples use 32 bits). @@ -191,6 +192,7 @@ struct spi_device { struct device dev; struct spi_controller *controller; u32 max_speed_hz; + u32 base_speed_hz; u8 bits_per_word; bool rt; #define SPI_NO_TX BIT(31) /* No transmit wire */ --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from BN8PR05CU002.outbound.protection.outlook.com (mail-eastus2azon11011030.outbound.protection.outlook.com [52.101.57.30]) (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 EFF363812EF; Wed, 27 May 2026 17:56:07 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.57.30 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904569; cv=fail; b=PRHx1S3oefRGWIVbFR5awqdDWh7B23C4J5MQJ1QlxUKIle2G5qzVDoWP7olLhk5iJAFBodr8nw6oZFVUg/7kpj7S+dsTVdW5l50J7WrWqA+cLSOHvBOcO1DaqE4udfT6o29V6/MbZTdkmiWY2mGn5pnQ9xBipyDDnDsuulA7HeA= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904569; c=relaxed/simple; bh=/xZZ5CprYTEb19MTJJpuLMyqZlQqZiBreMR2jUs/qZc=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=cbsFNoUHy5EkAe9xsa4/jqPZD+8TfeXl1r17vFJgv1wKLeRyqzPOCq7x9Oj9NjFVBrBJ+iFEnCMk5cojddcf+ElWj6dghb7NBZTitgZGVxivHFo16eaI3R48YXzwWo28T/ZitYdJmbd33hyMqB8g+97o+77/Kpc8a0dFoFNzqQ4= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=dfJk32hj; arc=fail smtp.client-ip=52.101.57.30 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="dfJk32hj" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=Xtur9GXwYeSHsCB6UyGrmK67xuL7rr7nXZEgcfp8+BPCTuB/5yk4QmSpR2V2C/VamALDNb0/GVBZKssrD3u/1q+pddvvcZxtK/2j61pnqP/tMZ2t/+rbTnf5QwlUG9qAcVQeJTfswqUmqc0ywUHM78VyVAtryVK3Tcwju4WojtVU17HaMxy2DjIRaBsH1SJZ7dmSpnLHIDxUVPM/hl7kYf21iqCMiFxoK4M89r1CcbzBTPXYhnTbgP42WJrOpStgB8n1rnHN1N4hQz3g7LzK0vxNFt75egftfPJchBAHhZ+cp1NeMBdUdbeFB5W4XN0IMFvEAmEi76yF/rTDR/2Hig== 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=rwqWvqj2lbEvHWX0JYLWZfMEbZuBSKzUibQivi4Zjw0=; b=UQ552KnbxsXomtpj3W/G0ebAIyehh1CPeWr1/EXpAvw/jpkT8hXiQSgIalUMpuoOAJUqs1lT7HOBgKGJEOKf3gVH8UND/gMs26QAHVGJ5vN1FTtFoJ2nPpLApUzkheC8rIx1TGNU0SnGMic52wpoAnoM53BmuMot1lYEnCsBNgSkZ9Mvo8T3vPfwhwypIhACJW9ddLEovan3bT8W+rKJLy/5EySBFud3e2umbnv0OpEWtWqhBq3d0JacbH7hE9vnS6/P8B0DXl/Tg2aHqAAJwM/T/EiPAoGPorbH6OEis0ggand7KYDhVAMfcmwp0EV4h+yBS0iCWj3SRHdfXmbJtg== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.23.194) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=rwqWvqj2lbEvHWX0JYLWZfMEbZuBSKzUibQivi4Zjw0=; b=dfJk32hjxZ+a5+8pf1WPj+KslWO7/pWyU1DqDSti6ZTSpzcYasSLX6px1jK4UIYiWG45l6i3OasLBo5whvCUhJCBKjGeR4oLedM9Tg0TVXxQkxVdyFpaRitqfw6if4zzeZ+oPj5P2/uZds/Qqb//51E9SJaoZdFFI74V/PD7X7s= Received: from CY5PR20CA0009.namprd20.prod.outlook.com (2603:10b6:930:3::22) by DS7PR10MB5997.namprd10.prod.outlook.com (2603:10b6:8:9f::18) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.48.18; Wed, 27 May 2026 17:56:04 +0000 Received: from DM2PEPF00003FC5.namprd04.prod.outlook.com (2603:10b6:930:3:cafe::7b) by CY5PR20CA0009.outlook.office365.com (2603:10b6:930:3::22) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:56:04 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.23.194) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.23.194 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.23.194; helo=lewvzet200.ext.ti.com; pr=C Received: from lewvzet200.ext.ti.com (198.47.23.194) by DM2PEPF00003FC5.mail.protection.outlook.com (10.167.23.23) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:03 +0000 Received: from DLEE210.ent.ti.com (157.170.170.112) by lewvzet200.ext.ti.com (10.4.14.103) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:00 -0500 Received: from DLEE202.ent.ti.com (157.170.170.77) by DLEE210.ent.ti.com (157.170.170.112) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:55:59 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DLEE202.ent.ti.com (157.170.170.77) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:55:59 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpg4052476; Wed, 27 May 2026 12:55:55 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 04/13] spi: spi-mem: add spi_mem_apply_base_freq_cap() Date: Wed, 27 May 2026 23:25:18 +0530 Message-ID: <20260527175527.2247679-5-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: DM2PEPF00003FC5:EE_|DS7PR10MB5997:EE_ X-MS-Office365-Filtering-Correlation-Id: 19fcc56c-0e21-472f-a468-08debc193854 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|36860700016|376014|82310400026|7416014|1800799024|921020|22082099003|6133799003|56012099006|18002099003; X-Microsoft-Antispam-Message-Info: /Nz9HidO1B73WXqHC7X+cSIY3/NdvbgH9fT0CnY7A7n0qMXj5gnEoOE3lufx9wJkwjjQZ6gS8eCI+di70RRQicSpek9gKwX9Gh/IIpC73ZXIQ2Nmj/+EEKM4JBgAtrnQxqDuhVGyQC8QIERknIeqKpy9n8aXKo/JL72Rxj9TDC/lBbmnnW+K/seR20IIABHUFZiaJgdjluyqyf5vHPYz0tqVDyeU30RozYaUx9GaD4Dq/4Eh9H370eRGs/EY5Ki6zRPRTUW+VkyFZJG71CofoW2JjL5dkrJBpBVpDz64wTaPR18ulLI+hfjA1KwKUXXsbTiSbqcODs832D5s+vVgIve8jnmvpF93JfYFFiPayAtPyCmmMb7uMFustSN9aBswc94T2e32pINp+xnmX46ae0hrwnBcqjIaivI6xPYpUR5+Lyvlz1TAu+Ahctd5iFpmDaY+dtjBSsdcAGGeUm3utJ0oPoQlnaZT58fGGd6fhUSVJVvfhvSru4Pb0qvZdC06keiQZxEkqJw3ToEmc6RI8d5eaOEYTYpZQfCcwswZHmkKgko5CVdnck+3+LtnvjLNMcgo6dx4WFWFRmFneydXxqkJ1zjW2ZMakEypkMHpoWA6I3hJ2M8WrW7sMkRzYn+/AwYEaKAPfiYi8TBSgMk7iGf173TH27XmDAEZNZTJUWA9HpV3kGAif4yNYJpPIZyYIc9+CKwXkKT2uO2Z7JmGsQQywz415vtvaYPNk5R6OjYyKcq8EUkYpdhe7FTqcfp/hr9ifvWyFLfuDBXZrpqCVQ== X-Forefront-Antispam-Report: CIP:198.47.23.194;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:lewvzet200.ext.ti.com;PTR:InfoDomainNonexistent;CAT:NONE;SFS:(13230040)(36860700016)(376014)(82310400026)(7416014)(1800799024)(921020)(22082099003)(6133799003)(56012099006)(18002099003);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: dVXDk4oyOYk2XFl+wKj/3URVaCGBRK8quiu04hbLoY+8FocCANHguV2d30gP0XrUZNHpVabdEWuQmB97KWaAHNLWsBwFn/PDLuxXpvRZ0msR6GqrQc5eKXNV7voOin9CFg9NOXVC4yset67AxrmCfCG86O7s0WYgSDjlhRe5hnlNAJp/8Cy6fWDSnApFzcdkVEURRjX5jx8/ohtFKZUTwTbUl7RmklKHy/l2FUelPrlaX5iFCYdNG4C6aytambfArvF21Prd1DogcuU0THwd9oij8hkBGoxxIMh9W+7k6zsAA3V1DlkPy5ZS2BtX3MuOiZf9dFt6S2NSv1HchDcFb2+L1d0Nl7gKDrw6nRBhRSAr8UzPAa8y+OjSUgFKtBr+rB+MwsCW4HmrN2tBo7qZVr1Yv+iT/LhLeVanJxX9kZF+TJbntu5Np+QvSUBnpWMp X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:03.7462 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 19fcc56c-0e21-472f-a468-08debc193854 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.23.194];Helo=[lewvzet200.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: DM2PEPF00003FC5.namprd04.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: DS7PR10MB5997 Content-Type: text/plain; charset="utf-8" When a device exposes both a conservative speed and a maximum speed, operations that have not been configured for max-speed use must be prevented from running at the device maximum. Without this, any op with max_freq =3D=3D 0 would be silently raised to max_speed_hz by spi_mem_adjust_op_freq(), bypassing the intended conservative limit. Add spi_mem_apply_base_freq_cap(). When base_speed_hz is set it caps op->max_freq to that value, unless the op already has max_freq set to max_speed_hz, which signals it has been configured for max-speed use. Call it in spi_mem_exec_op() before spi_mem_adjust_op_freq() so the final frequency is within both the base-speed constraint and the device maximum. Signed-off-by: Santhosh Kumar K --- drivers/spi/spi-mem.c | 26 +++++++++++++++++++++++++- include/linux/spi/spi-mem.h | 1 + 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/drivers/spi/spi-mem.c b/drivers/spi/spi-mem.c index a88b9f038356..d16986274cbc 100644 --- a/drivers/spi/spi-mem.c +++ b/drivers/spi/spi-mem.c @@ -398,7 +398,11 @@ int spi_mem_exec_op(struct spi_mem *mem, const struct = spi_mem_op *op) u8 *tmpbuf; int ret; =20 - /* Make sure the operation frequency is correct before going futher */ + /* + * Ops not configured for maximum speed are limited to the conservative + * base speed; spi_mem_adjust_op_freq() then caps to the device maximum. + */ + spi_mem_apply_base_freq_cap(mem, (struct spi_mem_op *)op); spi_mem_adjust_op_freq(mem, (struct spi_mem_op *)op); =20 dev_vdbg(&mem->spi->dev, "[cmd: 0x%02x][%dB addr: %#8llx][%2dB dummy][%4d= B data %s] %d%c-%d%c-%d%c-%d%c @ %uHz\n", @@ -599,6 +603,26 @@ void spi_mem_adjust_op_freq(struct spi_mem *mem, struc= t spi_mem_op *op) } EXPORT_SYMBOL_GPL(spi_mem_adjust_op_freq); =20 +/** + * spi_mem_apply_base_freq_cap() - Enforce the conservative base speed for + * operations that are not explicitly validated + * @mem: the SPI memory + * @op: the operation to adjust + * + * When @mem->spi->base_speed_hz is non-zero, caps @op->max_freq to that + * value unless @op->max_freq is already set to @mem->spi->max_speed_hz, + * which signals the operation has been configured for max-speed use. + */ +void spi_mem_apply_base_freq_cap(struct spi_mem *mem, struct spi_mem_op *o= p) +{ + if (!mem->spi->base_speed_hz || op->max_freq =3D=3D mem->spi->max_speed_h= z) + return; + + if (!op->max_freq || op->max_freq > mem->spi->base_speed_hz) + op->max_freq =3D mem->spi->base_speed_hz; +} +EXPORT_SYMBOL_GPL(spi_mem_apply_base_freq_cap); + /** * spi_mem_calc_op_duration() - Derives the theoretical length (in ns) of = an * operation. This helps finding the best variant diff --git a/include/linux/spi/spi-mem.h b/include/linux/spi/spi-mem.h index 722abd9aee3c..98125cb4cc6b 100644 --- a/include/linux/spi/spi-mem.h +++ b/include/linux/spi/spi-mem.h @@ -462,6 +462,7 @@ bool spi_mem_default_supports_op(struct spi_mem *mem, =20 int spi_mem_adjust_op_size(struct spi_mem *mem, struct spi_mem_op *op); void spi_mem_adjust_op_freq(struct spi_mem *mem, struct spi_mem_op *op); +void spi_mem_apply_base_freq_cap(struct spi_mem *mem, struct spi_mem_op *o= p); u64 spi_mem_calc_op_duration(struct spi_mem *mem, struct spi_mem_op *op); =20 bool spi_mem_supports_op(struct spi_mem *mem, --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from BL0PR03CU003.outbound.protection.outlook.com (mail-eastusazon11012004.outbound.protection.outlook.com [52.101.53.4]) (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 3E11430F55F; Wed, 27 May 2026 17:56:12 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.53.4 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904573; cv=fail; b=tofZ8adw0QMO1PUfgtrHlibn2lxv+OkRtrFLXQDRT90kxDYdU1NmYfmkTU9IdIaxTOimG8J1uyIHBVzM4vsU9jn4BwE4gMB9JjGOASQoK0kaRYHZu8T67UIHvpTgq7e8BDzo/NWnaBAGM7KuqrlTZBvD2/da1iguyzy5DMBob3M= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904573; c=relaxed/simple; bh=hIP1IHD41O7eTZCBBTWs02p28a/K/AxUz3PUEjPfIQ8=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=dD/KCU8nf7CD7yvLYuu0T0/INfiohZwILxaUQ9cJgGks+6vSEgLhg/FxlEFBR4ws94kwtIj/fXqAYP3jp4mB3nayxKWwmtbfpOqjxFp/PNDbm2C5SPuyzn4/sc5KNK9ARqOJTfol+pTzJIhaG4JYdz7BsRNJu6b+snkcyJsrqsA= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=iMYTQle1; arc=fail smtp.client-ip=52.101.53.4 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="iMYTQle1" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=UuvbxiH8uBSxnqmVpvzXkFaOyia0Quh9NKcQFpEaSuL+r/9sE1DG+55VbUhXdGg5SOs+3ts1vIy59Hb07eWNFn55Dk76tiXXXCbwzM9Oxb/i6llEnSP66+DVqu5Dt8/yYMxj2J2drOYQVQEeFCaSPC6MCulVNh85einp00Fw1JwolDrlY/FDB8xFjs9EoSGeabNWPH6tEI8bd8sbmY5E1GH05XOBfv3B7sIH91RLc4xYLIiIo38+g7yTnlnqlGUgd39lGBAMbaeeHlK5rk3t+V2yvihAlO6eG0D1Lp2+gu5/eqk5EQhQMS4Uv0RKHiz16y2RkipdshjWea0Xg/puxA== 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=0UxLwKEG9Sxpr4uyCaHjB7mQbecROYwET5VRDSWCabU=; b=vHezUULT5k62DpTzD8/N9Oi+JFjPCLOsmX9uq038pAuO2FIaktKRCuCqseVRGvNm86EjUmxpMp3TUojcMK/7I19YiKl4VFDzuOH5hmxXs2I4nUlc4ES6XAbPBZ1xR4XOJR8/7qjXY+Kk7TDI55lyDBwjez0IgB7TJkIycwKWJeyaY91qL8GnbgjHQcEq8OcKhqheDOyi38iMurdDmuRIS3a0bZwgPqE86FKnRpIaDBKVRUob7zKhC4MCuWEzSVRg4E1S/rit4KnwCx4NdHItEstedpvjVe6jugXzLNsimuSnM1EDa2BHl28/m9oAPPNamVSNp+I+CuFZDqAZZoNo7A== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=0UxLwKEG9Sxpr4uyCaHjB7mQbecROYwET5VRDSWCabU=; b=iMYTQle1hw2nyP67nyUxv5YnqIPoTGo6108kxgiiY//5SzX05OS1h9EpgCIkDhOeXS2Htr9qu+IXc07xTPxC6KTnRH8ynrRFSJLoRMbdg0emvYEn6pw2qKRpzVtT+I4mr7TD4TLdhhqfx7fiPXAFH+ExeMczIC+o0hogOJn6XKU= Received: from BY5PR03CA0001.namprd03.prod.outlook.com (2603:10b6:a03:1e0::11) by SJ2PR10MB7809.namprd10.prod.outlook.com (2603:10b6:a03:56f::18) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.12; Wed, 27 May 2026 17:56:07 +0000 Received: from CO1PEPF00012E5F.namprd05.prod.outlook.com (2603:10b6:a03:1e0:cafe::33) by BY5PR03CA0001.outlook.office365.com (2603:10b6:a03:1e0::11) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.48.19 via Frontend Transport; Wed, 27 May 2026 17:56:07 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E5F.mail.protection.outlook.com (10.167.249.68) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:05 +0000 Received: from DFLE205.ent.ti.com (10.64.6.63) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:05 -0500 Received: from DFLE201.ent.ti.com (10.64.6.59) by DFLE205.ent.ti.com (10.64.6.63) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:04 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE201.ent.ti.com (10.64.6.59) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:04 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYph4052476; Wed, 27 May 2026 12:56:00 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 05/13] spi: spi-mem: add execute_tuning callback and spi_mem_execute_tuning() Date: Wed, 27 May 2026 23:25:19 +0530 Message-ID: <20260527175527.2247679-6-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E5F:EE_|SJ2PR10MB7809:EE_ X-MS-Office365-Filtering-Correlation-Id: da9864c7-ae47-4818-1a5d-08debc193997 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|82310400026|36860700016|7416014|376014|1800799024|56012099006|6133799003|22082099003|18002099003|921020; X-Microsoft-Antispam-Message-Info: NTGY4UzjzSmRC+PzfdbQIq8RFuST4SbIOK6bhmDM3bEUqxdKZOz7dJn4fTsQqJkjWda2NIGaUsvAsyc3cOC6chI3zpi2iTT3ipP3x8FUY063RrEUGuZhM+GHTMMMdaqvN6NRQQgdVBO0bjeklOPVWMdRS2ee1BuefZYEynwDEjgWJcuwgIleFWN+1QSS1zQT/yyadh+MhRCSYSzfcUehrY6Yf3EQot6AKTpSbndQm/S7QJ7bJ3hOPuCoSYLSfAUmz/Gpm+swfXdEXIavS1W0+QzsG8rgeK+thAq7QDHNjAsh3HtSRghx8jzFCztd9OFm6yGo0+zsmcJ7pV1w2go07jr02wh8UC8Wz6cXi8FB1S40kCaNI9m4cAgprlRFRiJYpBagy5Mh4VMx9y2N6agnxhJ6ZJg7DN5k8jS9r2mVptnCxiR+mBZSXTNvWObcD64R61Q74pnpAxcZibJL9ZZkXkEcScP/cjVNHYH/HJKb96866N8Kf3ETrQNiv22/JWR/DOHxRGaQkZebaQU8RbIqFiBNGJav21iK8p+XykvZV6sTD04nmDTqN6XBY8f5uKIiyoj4eeKvlgbfFP1edrguyq1rY29nozm9+8V2w+OAzjM4vXZDS51I+7HIR5XAjSVXMKfBk4D39lhzBZjz6wIfWFLHTd1mDzlZ4qmgmWADOVTbFHrRkc24rYNj5wYy4HxpZ8AXGmLn8gzNVKmZxT8fGG2D/IRy0nyBTHzb26Sw50aL5TgoUdk2tBgpTyT8KTIeR7vjHluSWEQCQGrJIixzQQ== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(82310400026)(36860700016)(7416014)(376014)(1800799024)(56012099006)(6133799003)(22082099003)(18002099003)(921020);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: de6JEIZR5I5f0A8Hx9fRcV1WFipzC8nUU1d/BW+DKfOEQLNnUDslPU8SghRtAxpWZUsIrFDaAdSORxi7yAiw6d5LDqqPZTKSxkFV+ZGiUg+L6uf5EE7RL38tdBSPPSKJm9kbH93x4CrByQ1qFxNjo6Gqz/bISQsUrjdmoXnknG/uYymjkRL1y/IIdRDogNznPRXHp644He3qi2UQzB7OBGkAOZOo01dZnALH+TyzbTY+1Bg/AlMqB+DKMCe7+WbwbKLxm0esRGSpdMPhDGn1jCGgYLyBzNfkS2QwQ22HCI0rbSYjiHgmyuRmtzM6G7VPcqS3lABmI/FzWDwqJtdRpQRiUNuzCvKWF1ZZF19dVgW5Vd2hSt4LSGZOeOOhXiDob2G5czbd5QaghJdGJP05Xddci6GJDlYS6CQdT4QBhhWqOs3BbW1KhTQuVlJS0Mjp X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:05.8279 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: da9864c7-ae47-4818-1a5d-08debc193997 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E5F.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: SJ2PR10MB7809 Content-Type: text/plain; charset="utf-8" SPI memory controllers that support high-speed operating modes often require a tuning procedure to calibrate internal timing before operating at maximum frequency. There is currently no standard spi-mem interface for drivers to trigger this procedure. Add an execute_tuning callback to struct spi_controller_mem_ops. The callback receives a mandatory read op template and an optional write op template. On success the controller sets op->max_freq in each provided template to the validated clock rate. Add the corresponding spi_mem_execute_tuning() wrapper that validates inputs and returns -EOPNOTSUPP when the controller has not implemented the callback, allowing callers to handle controllers that do not support tuning gracefully. Signed-off-by: Santhosh Kumar K Reviewed-by: Miquel Raynal --- drivers/spi/spi-mem.c | 31 +++++++++++++++++++++++++++++++ include/linux/spi/spi-mem.h | 9 +++++++++ 2 files changed, 40 insertions(+) diff --git a/drivers/spi/spi-mem.c b/drivers/spi/spi-mem.c index d16986274cbc..5a4bf4b17fc1 100644 --- a/drivers/spi/spi-mem.c +++ b/drivers/spi/spi-mem.c @@ -675,6 +675,37 @@ u64 spi_mem_calc_op_duration(struct spi_mem *mem, stru= ct spi_mem_op *op) } EXPORT_SYMBOL_GPL(spi_mem_calc_op_duration); =20 +/** + * spi_mem_execute_tuning() - Execute controller tuning procedure + * @mem: the SPI memory device + * @read_op: read operation template (mandatory) + * @write_op: write operation template (optional, may be NULL) + * + * Requests the controller to perform tuning for high-speed operation + * using the provided op templates. On success the controller callback + * sets @read_op->max_freq (and @write_op->max_freq when non-NULL) to + * the validated clock rate. + * + * Return: 0 on success, -EINVAL if @mem or @read_op is NULL, + * -EOPNOTSUPP if controller doesn't support tuning, + * or a controller-specific error code on failure. + */ +int spi_mem_execute_tuning(struct spi_mem *mem, struct spi_mem_op *read_op, + struct spi_mem_op *write_op) +{ + struct spi_controller *ctlr; + + if (!mem || !read_op) + return -EINVAL; + + ctlr =3D mem->spi->controller; + if (!ctlr->mem_ops || !ctlr->mem_ops->execute_tuning) + return -EOPNOTSUPP; + + return ctlr->mem_ops->execute_tuning(mem, read_op, write_op); +} +EXPORT_SYMBOL_GPL(spi_mem_execute_tuning); + static ssize_t spi_mem_no_dirmap_read(struct spi_mem_dirmap_desc *desc, u64 offs, size_t len, void *buf) { diff --git a/include/linux/spi/spi-mem.h b/include/linux/spi/spi-mem.h index 98125cb4cc6b..2457ec6f63d6 100644 --- a/include/linux/spi/spi-mem.h +++ b/include/linux/spi/spi-mem.h @@ -346,6 +346,10 @@ static inline void *spi_mem_get_drvdata(struct spi_mem= *mem) * @poll_status: poll memory device status until (status & mask) =3D=3D ma= tch or * when the timeout has expired. It fills the data buffer wi= th * the last status value. + * @execute_tuning: run the controller tuning procedure using the provided + * read and optional write op templates. On success, set + * @read_op->max_freq (and @write_op->max_freq when non-NULL) + * to the validated clock rate. * * This interface should be implemented by SPI controllers providing an * high-level interface to execute SPI memory operation, which is usually = the @@ -376,6 +380,8 @@ struct spi_controller_mem_ops { unsigned long initial_delay_us, unsigned long polling_rate_us, unsigned long timeout_ms); + int (*execute_tuning)(struct spi_mem *mem, struct spi_mem_op *read_op, + struct spi_mem_op *write_op); }; =20 /** @@ -465,6 +471,9 @@ void spi_mem_adjust_op_freq(struct spi_mem *mem, struct= spi_mem_op *op); void spi_mem_apply_base_freq_cap(struct spi_mem *mem, struct spi_mem_op *o= p); u64 spi_mem_calc_op_duration(struct spi_mem *mem, struct spi_mem_op *op); =20 +int spi_mem_execute_tuning(struct spi_mem *mem, struct spi_mem_op *read_op, + struct spi_mem_op *write_op); + bool spi_mem_supports_op(struct spi_mem *mem, const struct spi_mem_op *op); =20 --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from CY7PR03CU001.outbound.protection.outlook.com (mail-westcentralusazon11010048.outbound.protection.outlook.com [40.93.198.48]) (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 A6D8945104C; Wed, 27 May 2026 17:56:15 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=40.93.198.48 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904577; cv=fail; b=LhsLu7LC7ft8GEOatd+iPcgzoeAVKj0NZ1MXvM6kEAG0lY7B0fPoV9/tzb6rF64RGfRrPZyQ6vyAxWgvGNaUBGwidhPIiWsY0ZsFwGXiTljzNqNVI2lmfjAWAw78FRErh0t4hjOhiZqtAcQ/mh0AJMIazkrHiqguTH2WdOvepSk= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904577; c=relaxed/simple; bh=1TNaL961Cge3k7wU6h0EQ4Y86FKi/4AiwNfqTwOJcWo=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=PiEPalmfu/2RvmW5bCBjImd+/y7PCNx3BISaqoGozZjE4OI5ojRvytTgI/Ttd2qWTzKYlj3/kmD43zbg1Gf5QpoBL3X0sEHjK8xB6UI5kUdw1YHldvj2u7ZITyTPCnmES+VoD3oHqcfMMgCK8RN3RGKZLOI2bYAi7mWjIUZsYdQ= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=L/zmP6Li; arc=fail smtp.client-ip=40.93.198.48 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="L/zmP6Li" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=cBw+jqDx63Kz0atSSIgc3BJvzKt38WPVDmvZI8PXD7OZO7ZrLoHxwiIGIgZ9gKMFmQpiRx+AAgn5hRdCXj5MXZFmHpbhKCFdgjE06xgJhtl6S4JxgevpiRb4NVkL+1NfS6X9wWDyFTeJyA7aSRknpNP7/OkodhIz2TQ1X6R1JA9kep0vvrSrD+IDYFKt2/GyOQO1aLUv8QYhWHaUPTQ5JBQjfg/Zl0+LRYOlNHdqK4YcUjnV6GRQI9iBjlmtzspRgM9ehLzrHGhh/pe2q0G48aFY/PxtilFmD6A34Ebk241MPXRABjuXSYJZFVz1v4C2OZsuItkLVDk6yeaWr4TgyQ== 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=mWYfQJUfKbZZJ9k0BCHgnlW6JIDDm6EOLXaVsX8Kde4=; b=jSsKqsZMpYRAR3EARLseomaEwBuBRz7D7GuaYTuKGuLaqNK1eVZCSCtLFixFJ6xco5/Vf9/LSHxIWaYYyJLgJOj+ZG17JHAax4UtoEaQj1/FgfmKQd5xCvGME24Vtn5RojiPoUHLFP1aOxa2wHmHzNQ/kORNrfpd6g0qZ9c3YFQNFtu5cv/ePnGn93sP7shSgQQEop9sBdGq0RKJ4NYVQcidzikvV8tTZmNaYBA9DNOX08haUY9aFagyXuXV+rA1pUufO0G2HMcGnaxsYTGU03cK0Mb3KvHZXPlbRf+Wv9VPaNAT35J2obdiZE7vzC6CsqYD1EenqaVY4Yd9FLkXdg== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=mWYfQJUfKbZZJ9k0BCHgnlW6JIDDm6EOLXaVsX8Kde4=; b=L/zmP6Li77sWBsL/IqyLbsmEfjM0ot/N2nYl57IwuMe9savxShZOt7PQedHHDP4mUSicxoHxKxzrVXG599EziNbxazcS0XAeYjT7akJoB0B9Jjkvrxi5wA2SyjamW62+FxUWDTX2k6IbOyDwyBfemPk0wbxJtFM8wuCj0o5HhCg= Received: from SJ0PR05CA0061.namprd05.prod.outlook.com (2603:10b6:a03:332::6) by BLAPR10MB5202.namprd10.prod.outlook.com (2603:10b6:208:306::15) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.13; Wed, 27 May 2026 17:56:13 +0000 Received: from CO1PEPF00012E60.namprd05.prod.outlook.com (2603:10b6:a03:332:cafe::31) by SJ0PR05CA0061.outlook.office365.com (2603:10b6:a03:332::6) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.92.4 via Frontend Transport; Wed, 27 May 2026 17:56:12 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E60.mail.protection.outlook.com (10.167.249.69) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:10 +0000 Received: from DFLE203.ent.ti.com (10.64.6.61) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:10 -0500 Received: from DFLE213.ent.ti.com (10.64.6.71) by DFLE203.ent.ti.com (10.64.6.61) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:10 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE213.ent.ti.com (10.64.6.71) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:09 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpi4052476; Wed, 27 May 2026 12:56:05 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 06/13] spi: cadence-quadspi: move cqspi_readdata_capture earlier Date: Wed, 27 May 2026 23:25:20 +0530 Message-ID: <20260527175527.2247679-7-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E60:EE_|BLAPR10MB5202:EE_ X-MS-Office365-Filtering-Correlation-Id: 07a07fcf-92de-495e-a3e9-08debc193c98 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|82310400026|36860700016|376014|1800799024|7416014|921020|56012099006|18002099003|22082099003; X-Microsoft-Antispam-Message-Info: Qx1TEEvu+qjQQxfwBPqZmwoVcZVtc2BqQlJVbTppBYsydKGGMsMOePBhjv7dCAVuCVY5Myvr2i4pxDiYj0TapUtEvvKO9W6kRgU9JcpRxECtVtzQPgHE8tAIInA9g5StCT0+FLSlTRzfgxJzJXlPYHLjDgC09iaAvCtLRep88tyR8oSaOuJDBfnvPT1gCTPB2mhubEQdjSG5fc5Eh0o4WQKzbdqvyJF2ZQG5HELbZOPkNMqXMfIZ96omVD7E8Zl24NL3UgkJJKSSkHuLwuuLjJYxDRFR1SHfIp3l6QJLKyqwdgyH1cEyquulO9Bsv9AD332sKsiamc2ypFobcHDlFE54bFsSojs0dIWvWdznOSVJUHX5Qrgu01E9aoQFhYPwDUiGiwRRIjFhJheJN1gT50UgDbs4h1SVfFZspxlGF8jAe5WcgyNTfOoOVBRpXTobwek0HwlX0MLLKbHUL/bEWr4M+OteweJCUOOzJgTGPm8Oy9nLTSLIJrxrRVAiRx5DzDKk+BMB4sQ+R72aGqoIUh7r6ov1jkPZX6kMrrNmPmiKMxMRRWqKBgb9KPfkHJfDrV+8zuFFikdW1//9jLvyx2TKhMLtHLnru+48PNOmFbvgOXjR7UoUOQDx/lHzAeMFNTV56USkmY9KynINXBV32L2XSGzv0B9sBxWL8sOUZmZr/eKXWi8wyhSNYZDRi9S0GUS6mDOmS2fCuW6SPfJSV1h+p2GYSZnbCkR99Cij9T3fkJLwsPmcH3wsZv/LQeWv72vwuif0Q88XQzLInJ+MIw== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(82310400026)(36860700016)(376014)(1800799024)(7416014)(921020)(56012099006)(18002099003)(22082099003);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: ooxmCpSg+/LaJUFxMrxS7+EYBsW8ZiiagxzZsR5avvZ1McwgfOa2DpkK+1EJftZ0yZD/lgZx8yPiu8Zeb/8laQlSXK3y6gnwmQWiE6SFMoBAi33cSLXp9AnSOOaprd5+KIRbpAh1dvzJQ3R5kIIcBz+YruKL3tDz4PX3kITyf/jzC2URYyKWNb01OtjgeJciyr2DqQjCmSrbcP/x1LWrE1g5AWQ/Ju09IcwHs1xL2nVp3AaxahEIvKKTw9xlJb6j0bT3Le/9jegSAWTkyfSEkmoOKW1aGNFhs/PDpyk25On8TKWi1eyvwnbf9EK18bjkspGx7nxHwgC0m1WEkmCGGTpT4w/qfDQUEvmAATYRL/OCKK7NatQ6pt7ZllkxAZ0RcUZiKItSWFM0wfo8vZhzInWF/zgZJMNiYjTCGp54Tf7xut/zN6UG2wOYLXAam7lX X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:10.8670 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 07a07fcf-92de-495e-a3e9-08debc193c98 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E60.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: BLAPR10MB5202 Content-Type: text/plain; charset="utf-8" Move cqspi_readdata_capture() function earlier in the file. This is preparatory refactoring for upcoming PHY tuning support for read and write operations. No functional changes. Reviewed-by: Miquel Raynal Signed-off-by: Santhosh Kumar K --- drivers/spi/spi-cadence-quadspi.c | 45 +++++++++++++++---------------- 1 file changed, 22 insertions(+), 23 deletions(-) diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-qu= adspi.c index aaba1a3ad577..54fd7b591e06 100644 --- a/drivers/spi/spi-cadence-quadspi.c +++ b/drivers/spi/spi-cadence-quadspi.c @@ -453,6 +453,28 @@ static int cqspi_wait_idle(struct cqspi_st *cqspi) } } =20 +static void cqspi_readdata_capture(struct cqspi_st *cqspi, const bool bypa= ss, + const unsigned int delay) +{ + void __iomem *reg_base =3D cqspi->iobase; + unsigned int reg; + + reg =3D readl(reg_base + CQSPI_REG_READCAPTURE); + + if (bypass) + reg |=3D BIT(CQSPI_REG_READCAPTURE_BYPASS_LSB); + else + reg &=3D ~BIT(CQSPI_REG_READCAPTURE_BYPASS_LSB); + + reg &=3D ~(CQSPI_REG_READCAPTURE_DELAY_MASK + << CQSPI_REG_READCAPTURE_DELAY_LSB); + + reg |=3D (delay & CQSPI_REG_READCAPTURE_DELAY_MASK) + << CQSPI_REG_READCAPTURE_DELAY_LSB; + + writel(reg, reg_base + CQSPI_REG_READCAPTURE); +} + static int cqspi_exec_flash_cmd(struct cqspi_st *cqspi, unsigned int reg) { void __iomem *reg_base =3D cqspi->iobase; @@ -1270,29 +1292,6 @@ static void cqspi_config_baudrate_div(struct cqspi_s= t *cqspi) writel(reg, reg_base + CQSPI_REG_CONFIG); } =20 -static void cqspi_readdata_capture(struct cqspi_st *cqspi, - const bool bypass, - const unsigned int delay) -{ - void __iomem *reg_base =3D cqspi->iobase; - unsigned int reg; - - reg =3D readl(reg_base + CQSPI_REG_READCAPTURE); - - if (bypass) - reg |=3D BIT(CQSPI_REG_READCAPTURE_BYPASS_LSB); - else - reg &=3D ~BIT(CQSPI_REG_READCAPTURE_BYPASS_LSB); - - reg &=3D ~(CQSPI_REG_READCAPTURE_DELAY_MASK - << CQSPI_REG_READCAPTURE_DELAY_LSB); - - reg |=3D (delay & CQSPI_REG_READCAPTURE_DELAY_MASK) - << CQSPI_REG_READCAPTURE_DELAY_LSB; - - writel(reg, reg_base + CQSPI_REG_READCAPTURE); -} - static void cqspi_configure(struct cqspi_flash_pdata *f_pdata, unsigned long sclk) { --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from BL0PR03CU003.outbound.protection.outlook.com (mail-eastusazon11012012.outbound.protection.outlook.com [52.101.53.12]) (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 1D362453482; Wed, 27 May 2026 17:56:19 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.53.12 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904581; cv=fail; b=hNkwsNhNBAmJ3Mkpkmq1xvF9i0L9RHZOo/usjBFpaf36e8BgMo4P9LXQ729OIqRwvWCoSays2X75DI2OxB+I/xtli/gJMjwsdL31/YHC4s+jK/S5ASv8ozpBlq/xY4SsAwai4WtqaGh2oDTxLUGj714s08KmmLiasbx/oQc3fmU= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904581; c=relaxed/simple; bh=jw3B9yi+hmX7DsJIwVzasLjy4Zy1mAqhau2w2IMS3zQ=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=qMeU4MNj4kFSzE83LVwNET85tDMf1EHLGS1ofUec+EimjjmLVoakL1ju8zS9n27CtklIn5uJlHRoGWBfUw+sezRiAvUOVxSJLcaaDjDbOxOO7TuB/A1LLrSmLp6W+fMLZzb3KKgU4LUr3/IYvzsUgmIsiS+nqE4N+HQEjPA7Biw= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=Vf/wyarM; arc=fail smtp.client-ip=52.101.53.12 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="Vf/wyarM" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=aGPYa4urTMhKgSE+UDo5IkB2Zj2mgA8yITBhO54K5BLWbN7rOiaHJEV4bnJXkjVkU5tdbzK9MSYX1FiIieytGbYv+/T7owFtY36NM2ZLUwEUunM5JmZentWc+9QR6+AhCBCoJL2leyren39Kj2pj3sUVayKm8nss2VwAePUaFiW6Y6cjl76GNYOEUW2aXbkbjOjDh+jGF7o6MMYbyysn3nsv4V3qHW6sd7eVy0bLbP4zb8oUjLR8cL4EvLcEvc7xnmAJKwBpn94OMjTXEbiACOpSOB1DGzNPEMHLOse3M+S5eP0js3RI5jNiPx2/IBgAuAYWIYmWmrNTEp5ki4Jn0w== 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=wCZc0wIVBtDCh1p0IprYueCIB6QFm2p/C8s4JQKghv4=; b=mFWk0xx6s+8jxWNtzcHG/xfAAT0KHY7zd5xu7+1KfkLm5Bv+qpVlkKdAKicbyJ7wK3kclMMzLrTTyKSYgI6JNu7y10xcPdoDB0eWzZq7+4fpeL4Ov3gjWJWt+GhpKoMSfSovLuyE7QJTS2XyUfM77P19COB/anQQJzS7cIC4ox4x77EstoVL7igp8k6MM4JViEI2oeBEkICzfx+6zvb04UZGJNmvWlYAryes+u1WGJqO8fsCVnOtydrqSzqAvFFlOBk0pPzg281t+QKeHKzNSbzOFyaCgRNH0+ZJLo881RDSDod+1WwP4/imN+0Bcc0VcrOdMFug2geVckMIt/88+Q== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.23.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=wCZc0wIVBtDCh1p0IprYueCIB6QFm2p/C8s4JQKghv4=; b=Vf/wyarMeeKLkeES1MpjBffWjlbAVLAl/0pB0k/3pv5gJEUnGNAPp085C8MORyVqRIjYWl3WQx+U4AyEagTmCfUNolegdQZ7fkkEwLb9UMaAu6G+NiiM1yWCBLXYn11r4xkqs1J4zAUB5TxzOEIIyFXpxpa1uAf2CV3lwqNBb2M= Received: from BL1PR13CA0399.namprd13.prod.outlook.com (2603:10b6:208:2c2::14) by CH0PR10MB7499.namprd10.prod.outlook.com (2603:10b6:610:182::9) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.12; Wed, 27 May 2026 17:56:16 +0000 Received: from BL02EPF0001A104.namprd05.prod.outlook.com (2603:10b6:208:2c2:cafe::45) by BL1PR13CA0399.outlook.office365.com (2603:10b6:208:2c2::14) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.92.4 via Frontend Transport; Wed, 27 May 2026 17:56:16 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.23.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.23.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.23.195; helo=lewvzet201.ext.ti.com; pr=C Received: from lewvzet201.ext.ti.com (198.47.23.195) by BL02EPF0001A104.mail.protection.outlook.com (10.167.241.135) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:15 +0000 Received: from DLEE208.ent.ti.com (157.170.170.97) by lewvzet201.ext.ti.com (10.4.14.104) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:15 -0500 Received: from DLEE206.ent.ti.com (157.170.170.90) by DLEE208.ent.ti.com (157.170.170.97) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:15 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DLEE206.ent.ti.com (157.170.170.90) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:15 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpj4052476; Wed, 27 May 2026 12:56:10 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 07/13] spi: cadence-quadspi: add DQS support to read data capture Date: Wed, 27 May 2026 23:25:21 +0530 Message-ID: <20260527175527.2247679-8-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: BL02EPF0001A104:EE_|CH0PR10MB7499:EE_ X-MS-Office365-Filtering-Correlation-Id: 1bfa5813-ee36-49c0-7eb6-08debc193f97 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|7416014|376014|36860700016|82310400026|1800799024|921020|22082099003|18002099003|56012099006; X-Microsoft-Antispam-Message-Info: ktZxFcILR5khN7Tkxq20pUSwZiBAz6SmmqnMmOS0+9jQWJWaRLtcYqfO+/fsT7e+h3QjFiHCRPcv6S05ivxtMvKexweUeTCYBWFf3wdC3aSe08WeDI4gUvgWYxhhjTtG5pyL7vcrPF13Q2RLbWEsU+vuTccHT26gRQadeS3PwBO5GX5Sf8n8SqJ1KbONJCBt4cAwaTQirBQVW3QcDxtJr+IW7Ka3Y8zvAe2SNWFhhzNNhOO0lBXwHInsjkqQM6YWk49w4EY7psiUTwtP287iqe3p3aDPGYQ5hpfQbTfb7L/r/tQLVpAxEEqUDJVQFcOfmm4oD4MbIA/tzGenpGU86P1FEb1KBXvtYl26mZv7fe/M2GjYF8PR+2X9Ftk2FE/XPze2e8gALKroYMhlDEuagIFPK2SmmimApQ4EVRo7hXxvrA8XCqWNluHHk1itO4BVN2tVk2H5EQ5KN+C42s7H06CCJQpj/1SVb0qllTexEFadFY45ERyHbiQYnPBAvchOtVRMmYbajKWrErzLXPGMcgEykky54Xf53/HbYSwYTRCXXLLXRtFij/aSpqonzs5tmu9GJOlLZIMgMaqv+NdCSyv+XrFop009DcFFHw1CUEwvozgCCKALAqm9UfT/jxrTfQeaF0FlNUgLvQq7bik/4stDhaQnmpMae0T3HEZcA+NCfuuJmOrjx38xD3hmDTvtmxCDxs4qcdaXMz0b/WBYYUrZUcDxdlNWcx84DxV/ZAsAqw/HdmpMIIZM4ayYsMRsMDUBAPwuuWXPRnDudRXhNg== X-Forefront-Antispam-Report: CIP:198.47.23.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:lewvzet201.ext.ti.com;PTR:InfoDomainNonexistent;CAT:NONE;SFS:(13230040)(7416014)(376014)(36860700016)(82310400026)(1800799024)(921020)(22082099003)(18002099003)(56012099006);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: iaE+IPvLxk/qYPVo7vizfqsg1hUlIA795a4pavZyGLWegiNGNPWKjTtYJmsrih1U6DZpZBsbTeaET/E7tEGi/ORqOTTfOW4PiCLlCy99MhkafnPaqyIpuAfbkfZU3D5r5ZfXAhWwwQOrQEjJFgdGYyFywZADYBGvpcsvYdfeuw21kdBHooZ0dxkGPVxlLUpY3SYb7l9wcjQl8beHp+QSeaJxBAsa2Ew3lIVBZKgGjomU7FExLbeF8BpR53TK/mXYM7yvOsa+qWnKEHcPiiDeTgEFpvBP0r9YQUdaulbpH6EG+/j2Vf+d3ohpOhAVQxUrwws3LmORncoOdR9rY3hGYHRcKL/WrvZYUgBZDbEKvzAKyFrgqZ6StprJMAv8fvjFC2WFF5zArH78itswInklV4vOLVhZwbXCSPKFrvkOOyd1X3iyPJ0UK/ks3BQsfe9T X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:15.8952 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 1bfa5813-ee36-49c0-7eb6-08debc193f97 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.23.195];Helo=[lewvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: BL02EPF0001A104.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: CH0PR10MB7499 Content-Type: text/plain; charset="utf-8" Add DQS (Data Strobe) parameter to cqspi_readdata_capture() to control data capture timing. DQS mode uses a dedicated strobe signal for improved timing margins in high-speed SPI modes. Reviewed-by: Miquel Raynal Signed-off-by: Santhosh Kumar K --- drivers/spi/spi-cadence-quadspi.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-qu= adspi.c index 54fd7b591e06..201d69c64c49 100644 --- a/drivers/spi/spi-cadence-quadspi.c +++ b/drivers/spi/spi-cadence-quadspi.c @@ -192,6 +192,7 @@ struct cqspi_driver_platdata { #define CQSPI_REG_READCAPTURE_BYPASS_LSB 0 #define CQSPI_REG_READCAPTURE_DELAY_LSB 1 #define CQSPI_REG_READCAPTURE_DELAY_MASK 0xF +#define CQSPI_REG_READCAPTURE_DQS_LSB 8 =20 #define CQSPI_REG_SIZE 0x14 #define CQSPI_REG_SIZE_ADDRESS_LSB 0 @@ -454,7 +455,7 @@ static int cqspi_wait_idle(struct cqspi_st *cqspi) } =20 static void cqspi_readdata_capture(struct cqspi_st *cqspi, const bool bypa= ss, - const unsigned int delay) + const bool dqs, const unsigned int delay) { void __iomem *reg_base =3D cqspi->iobase; unsigned int reg; @@ -472,6 +473,11 @@ static void cqspi_readdata_capture(struct cqspi_st *cq= spi, const bool bypass, reg |=3D (delay & CQSPI_REG_READCAPTURE_DELAY_MASK) << CQSPI_REG_READCAPTURE_DELAY_LSB; =20 + if (dqs) + reg |=3D BIT(CQSPI_REG_READCAPTURE_DQS_LSB); + else + reg &=3D ~BIT(CQSPI_REG_READCAPTURE_DQS_LSB); + writel(reg, reg_base + CQSPI_REG_READCAPTURE); } =20 @@ -1313,7 +1319,7 @@ static void cqspi_configure(struct cqspi_flash_pdata = *f_pdata, cqspi->sclk =3D sclk; cqspi_config_baudrate_div(cqspi); cqspi_delay(f_pdata); - cqspi_readdata_capture(cqspi, !cqspi->rclk_en, + cqspi_readdata_capture(cqspi, !cqspi->rclk_en, false, f_pdata->read_delay); } =20 --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from SN4PR2101CU001.outbound.protection.outlook.com (mail-southcentralusazon11012044.outbound.protection.outlook.com [40.93.195.44]) (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 7B6673812EF; Wed, 27 May 2026 17:56:26 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=40.93.195.44 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904590; cv=fail; b=DLL54NQ8/RrDsU4PUQVTcUwWdT+V1GrVWzAszr+8jeVBmlWOHQel8TX6VJ5thK9cz4lv9DvuD/qfW2xeoDlxGHgDqgRdtufzrmZ4d/ok3YGvAmv8/JqJceL0ebiN4kHXGBQyVQp51iXAp4GVa4wspYOCwE9CCBiROKuwKOsPpkk= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904590; c=relaxed/simple; bh=AKHc95MYz1MbvZshQ2I3Mx5efqadnZZ0suGVzIzpm24=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=JIwDH4GoACu4ZIgpUhzbMj0MUAX2E3qD0v7U7tEUgJOOcndfzo0wN6Mf9yo7YcnXTFRJ/eo/wYXLEsm1vDUq9ooZrHRCBjsXQJTJ79mE9rLfH0rosoplK3C/oVygF9VQG2H0CpMBHp5WEcqQUmUUT/6RLMlEHHCstAU2fU376Xs= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=OqwbKZBZ; arc=fail smtp.client-ip=40.93.195.44 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="OqwbKZBZ" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=ShPB1dpASxrLyp5WCHnkwcTgJFHgyhizUkmAi0KJ0cNGuZlA7cWB7esntqJGUj7xLkelUMaV75gx0G6pDQPd9pAGCf1bK1/3uJEU6kIR9gIUTEXTOOqk3pXNx9NAq8V7sN1wY0+ENeVSxZoucB6w6vYVwJLp0k+8vO6QE5T0vlSyoBynr+zrUB0u7Hg7n2VNavtFkrA0/66yStUEyzA7Qawso+TNuT3NHrbPcaNjg5LHgdAddqa3d6WvkFzgZFlir10xi46O+CdTfWAo4yGHgzrVEW/7Cn0vG/n9EXH9qGsS2q11r8WZvKnKPotSU74bYUbEH6ukp3/zSV2UZtULUA== 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=SXudC3Ii7VUYcQH2RLHZ6KIH7L3RimW0d4UdgPxGy/A=; b=cMhYRHHXnSktZPdlZlw9Qu0SZ+pFmIN5wgQENzmTiT0PT79ahZ3RfEGPLmUNfr0Whk8PwFoLM+eYQXsNgPfk/S2Dm5uzHF0Kp0FhiEKGGaoKZow/6X7gLfm0IQx07yRBcBvh0NfA35elk3WL/Ncsml0xiJ+f/3qrqXBej8wKL0ZXI3A4R86w+/pEyYsaf7mgW6fsy7UUMVkcDnmjCXvY1QoEU3kbB5nyrVgTIjVCZMIeADVf8L/xZ4OSHlJ7p94K9jIO2XltAN11WsMMLI5V9tGxri9Q/yVaZX4z0ukxcZu/2sCkxgfu3ycQd+mZnaYWnsEWZlRwZKlUSyw31XpatQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=SXudC3Ii7VUYcQH2RLHZ6KIH7L3RimW0d4UdgPxGy/A=; b=OqwbKZBZv9I+JXGTOGARN34RAfEKAw+Rbk8VxEQFahJSWrvffKDhQHGd2ZfyQmYwOFRNFyQF207AUFAtnNCki41IrpvQscgdKs3Rc+iaSdnhz2Y0WFHDMvir8ydQFxA7wjmmE6eboRHoYPsFR2BGZ6hfL2432knlWULch8bAiq4= Received: from SJ0PR05CA0050.namprd05.prod.outlook.com (2603:10b6:a03:33f::25) by PH0PR10MB5547.namprd10.prod.outlook.com (2603:10b6:510:da::19) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.13; Wed, 27 May 2026 17:56:23 +0000 Received: from CO1PEPF00012E65.namprd05.prod.outlook.com (2603:10b6:a03:33f:cafe::17) by SJ0PR05CA0050.outlook.office365.com (2603:10b6:a03:33f::25) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.11 via Frontend Transport; Wed, 27 May 2026 17:56:22 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E65.mail.protection.outlook.com (10.167.249.74) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:21 +0000 Received: from DFLE208.ent.ti.com (10.64.6.66) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:20 -0500 Received: from DFLE212.ent.ti.com (10.64.6.70) by DFLE208.ent.ti.com (10.64.6.66) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:20 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE212.ent.ti.com (10.64.6.70) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:20 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpk4052476; Wed, 27 May 2026 12:56:15 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 08/13] spi: cadence-quadspi: add PHY tuning support Date: Wed, 27 May 2026 23:25:22 +0530 Message-ID: <20260527175527.2247679-9-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E65:EE_|PH0PR10MB5547:EE_ X-MS-Office365-Filtering-Correlation-Id: c995d540-8e85-4031-776b-08debc1942cd X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|1800799024|82310400026|7416014|36860700016|376014|921020|18002099003|22082099003|6133799003|3023799007|5023799004|56012099006; X-Microsoft-Antispam-Message-Info: VgrSbHypbNgYvADJofV+5ksM7CmENlsdHQq+utlON+kuRQqAWXzP8/Zkxdct+sx12dNC+NvwoE0jdhlkCtqUpT3gVrnFoiLwEsoF4XznzLCZ+ShZPsqeGuv+zpIzOGW5dMig7KddheVTHFVr0KDrDceI+auV9ij8UzgsW1eQn2guNOCdAeDsolB63ViMc80mS+dDYzBDXnUiyfGeOYjOKdxf5LF+qeArY1rPPqXMHNG24hQrD86EeRzqi6HxhKG8WzUYvW35Dsx+x0RXlxCGRzitG4cgr/dMKrodeu6XrjY3E2cXi3QP3xh0EubvF2Y7MW1gXL8FdUzBwkvBa3+5PrgQmhDIYMrhwipUGWgSkEJVjd6bqlucKGhxoQGX4TPBvgC9mGmg4oqPNSSg1fwUsqdtp2nF3B+6Ud56j+WfdJ5u/mCzBodilp6zpv4gKkvW7zvFTeo36kgkeoJXKkcOAKqpb5SZj76eMC3UvOTHVecXgKzqifkeQqM2xK9JVakbdWV3n/jgstfYKBj6TzStnhewoXVWw9Pq3Thlmva41Ifom++TLdVKV/BHg0tLIk9Ow0DPo/XEaMjttdLt447KC7UeMlqtBG0P/fURZdC6f86w4BI3yr5aUF0U/Mv0BEX4joRaAlQNjSu7ned/00cbiM9J2BdxYCc3fSBpOgCSyiQp7OW9yUuGppfGzfudAhPe6M+w3SIr7xILw+YHjiVN2wLvH2RHzaVGKXR1KVzz2J5lbb09eCf9u6rUEWbfriL3GqLBnWj1TUu1kvoHXiKiyQ== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(1800799024)(82310400026)(7416014)(36860700016)(376014)(921020)(18002099003)(22082099003)(6133799003)(3023799007)(5023799004)(56012099006);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: Ve9oH1FbMVSZJ5VF1AagCUYyTA0b/0pb2RgMWoDj4Mzdr9wvfvXO/cxioQU9Vp6uon7TAPDCe71d7wPZqhEr+fUMl/uviL1zSedBhPNkPEdKd4/7h0TjnQdYsvIB/WxC5t1pO+rDuYER/D8kZh0eWk7ieEq8t2lW0UcowuVR2u6q8rsnbVSkr7EBHVSKAJTtGLigQvXdW8wtcwo+cALPZuIBDvUa3NinL+bV2b2Rf4y9WkNuI6kXmIHQJsS8jxltkJa00g2MDWaCdfQOnjmgrK9W6lgDi55ubHf3cyGfPcERbA/qpBJV0WwFgZ+xGCAxWib8gVbpnYvElacWtoELyeg8fodB7GYSJGgJ4xwntgZakarccohI6F0QeBbCL0+mc1KKk1vPHvEU6wtXDLAKMfgGq5fE5pOKHeX1lhM2C6FClwQjsHtikGDrlj5nn1mW X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:21.2760 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: c995d540-8e85-4031-776b-08debc1942cd X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E65.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: PH0PR10MB5547 The Cadence QSPI controller supports a delay-line PHY for high-speed operation. Without calibration the PHY is unused and read capture relies on a fixed delay, limiting throughput at frequencies above the base operating speed. Add an execute_tuning callback that performs delay-line calibration using a known data pattern written to a dedicated flash region. The pattern is either read from a NOR partition identified by the DT property cdns,phy-pattern-partition, or written to the NAND page cache before each calibration read. For DDR protocols (8D-8D-8D) a 2D sweep of (rx_delay, tx_delay) pairs is performed to find the widest passing region in the combined RX/TX space. Binary search locates the gap boundary between passing regions when two separate windows exist; the final operating point is placed at the centre of the larger region with a small temperature-dependent offset. For SDR protocols a 1D sweep of the RX delay is sufficient. Two windows at adjacent read_delay values are measured; the wider one's midpoint is selected. The tuning infrastructure is platform-specific: only am654-based OSPI controllers populate the execute_tuning hook. All other platform data entries return -EOPNOTSUPP and are unaffected. spi-max-frequency may carry two values in DT; the second (higher) value is the tuned target rate stored in max_clk_rate. When only one value is present max_clk_rate is zero and tuning is skipped. Signed-off-by: Santhosh Kumar K --- drivers/spi/spi-cadence-quadspi.c | 1798 ++++++++++++++++++++++++++++- 1 file changed, 1789 insertions(+), 9 deletions(-) diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-qu= adspi.c index 201d69c64c49..508bc5bc4ab5 100644 --- a/drivers/spi/spi-cadence-quadspi.c +++ b/drivers/spi/spi-cadence-quadspi.c @@ -65,15 +65,26 @@ enum { =20 struct cqspi_st; =20 +struct phy_setting { + u8 rx; + u8 tx; + u8 read_delay; +}; + struct cqspi_flash_pdata { - struct cqspi_st *cqspi; - u32 clk_rate; - u32 read_delay; - u32 tshsl_ns; - u32 tsd2d_ns; - u32 tchsh_ns; - u32 tslch_ns; - u8 cs; + struct cqspi_st *cqspi; + u32 max_clk_rate; + u32 read_delay; + u32 tshsl_ns; + u32 tsd2d_ns; + u32 tchsh_ns; + u32 tslch_ns; + bool use_dqs; + bool use_phy; + u8 cs; + struct phy_setting phy_setting; + struct spi_mem_op phy_read_op; + struct spi_mem_op phy_write_op; }; =20 static const struct clk_bulk_data cqspi_clks[CLK_QSPI_NUM] =3D { @@ -129,12 +140,15 @@ struct cqspi_driver_platdata { int (*indirect_read_dma)(struct cqspi_flash_pdata *f_pdata, u_char *rxbuf, loff_t from_addr, size_t n_rx); u32 (*get_dma_status)(struct cqspi_st *cqspi); + int (*execute_tuning)(struct spi_mem *mem, struct spi_mem_op *read_op, + struct spi_mem_op *write_op); }; =20 /* Operation timeout value */ #define CQSPI_TIMEOUT_MS 500 #define CQSPI_READ_TIMEOUT_MS 10 #define CQSPI_BUSYWAIT_TIMEOUT_US 500 +#define CQSPI_DLL_TIMEOUT_US 300 =20 /* Runtime_pm autosuspend delay */ #define CQSPI_AUTOSUSPEND_TIMEOUT 2000 @@ -148,12 +162,14 @@ struct cqspi_driver_platdata { /* Register map */ #define CQSPI_REG_CONFIG 0x00 #define CQSPI_REG_CONFIG_ENABLE_MASK BIT(0) +#define CQSPI_REG_CONFIG_PHY_EN BIT(3) #define CQSPI_REG_CONFIG_ENB_DIR_ACC_CTRL BIT(7) #define CQSPI_REG_CONFIG_DECODE_MASK BIT(9) #define CQSPI_REG_CONFIG_CHIPSELECT_LSB 10 #define CQSPI_REG_CONFIG_DMA_MASK BIT(15) #define CQSPI_REG_CONFIG_BAUD_LSB 19 #define CQSPI_REG_CONFIG_DTR_PROTO BIT(24) +#define CQSPI_REG_CONFIG_PHY_PIPELINE BIT(25) #define CQSPI_REG_CONFIG_DUAL_OPCODE BIT(30) #define CQSPI_REG_CONFIG_IDLE_LSB 31 #define CQSPI_REG_CONFIG_CHIPSELECT_MASK 0xF @@ -192,6 +208,7 @@ struct cqspi_driver_platdata { #define CQSPI_REG_READCAPTURE_BYPASS_LSB 0 #define CQSPI_REG_READCAPTURE_DELAY_LSB 1 #define CQSPI_REG_READCAPTURE_DELAY_MASK 0xF +#define CQSPI_REG_READCAPTURE_EDGE_LSB 5 #define CQSPI_REG_READCAPTURE_DQS_LSB 8 =20 #define CQSPI_REG_SIZE 0x14 @@ -273,6 +290,27 @@ struct cqspi_driver_platdata { #define CQSPI_REG_POLLING_STATUS 0xB0 #define CQSPI_REG_POLLING_STATUS_DUMMY_LSB 16 =20 +#define CQSPI_REG_PHY_CONFIG 0xB4 +#define CQSPI_REG_PHY_CONFIG_RX_DEL_LSB 0 +#define CQSPI_REG_PHY_CONFIG_RX_DEL_MASK 0x7F +#define CQSPI_REG_PHY_CONFIG_TX_DEL_LSB 16 +#define CQSPI_REG_PHY_CONFIG_TX_DEL_MASK 0x7F +#define CQSPI_REG_PHY_CONFIG_DLL_RESET BIT(30) +#define CQSPI_REG_PHY_CONFIG_RESYNC BIT(31) + +#define CQSPI_REG_PHY_DLL_MASTER 0xB8 +#define CQSPI_REG_PHY_DLL_MASTER_INIT_DELAY_LSB 0 +#define CQSPI_REG_PHY_DLL_MASTER_INIT_DELAY_VAL 16 +#define CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_LEN 0x7 +#define CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_LSB 20 +#define CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_3 0x2 +#define CQSPI_REG_PHY_DLL_MASTER_BYPASS BIT(23) +#define CQSPI_REG_PHY_DLL_MASTER_CYCLE BIT(24) + +#define CQSPI_REG_DLL_OBS_LOW 0xBC +#define CQSPI_REG_DLL_OBS_LOW_DLL_LOCK BIT(0) +#define CQSPI_REG_DLL_OBS_LOW_LOOPBACK_LOCK BIT(15) + #define CQSPI_REG_OP_EXT_LOWER 0xE0 #define CQSPI_REG_OP_EXT_READ_LSB 24 #define CQSPI_REG_OP_EXT_WRITE_LSB 16 @@ -321,6 +359,50 @@ struct cqspi_driver_platdata { =20 #define CQSPI_REG_VERSAL_DMA_VAL 0x602 =20 +#define CQSPI_PHY_INIT_RD 1 +#define CQSPI_PHY_MAX_RD 4 +#define CQSPI_PHY_MAX_DELAY 127 +#define CQSPI_PHY_DDR_SEARCH_STEP 4 +#define CQSPI_PHY_TX_LOOKUP_LOW_START 28 +#define CQSPI_PHY_TX_LOOKUP_LOW_END 48 +#define CQSPI_PHY_TX_LOOKUP_HIGH_START 60 +#define CQSPI_PHY_TX_LOOKUP_HIGH_END 96 +#define CQSPI_PHY_RX_LOW_SEARCH_START 0 +#define CQSPI_PHY_RX_LOW_SEARCH_END 40 +#define CQSPI_PHY_RX_HIGH_SEARCH_START 24 +#define CQSPI_PHY_RX_HIGH_SEARCH_END 127 +#define CQSPI_PHY_TX_LOW_SEARCH_START 0 +#define CQSPI_PHY_TX_LOW_SEARCH_END 64 +#define CQSPI_PHY_TX_HIGH_SEARCH_START 78 +#define CQSPI_PHY_TX_HIGH_SEARCH_END 127 +#define CQSPI_PHY_SEARCH_OFFSET 8 + +#define CQSPI_PHY_DEFAULT_TEMP 45 +#define CQSPI_PHY_MIN_TEMP -45 +#define CQSPI_PHY_MAX_TEMP 130 +#define CQSPI_PHY_MID_TEMP (CQSPI_PHY_MIN_TEMP + \ + ((CQSPI_PHY_MAX_TEMP - \ + CQSPI_PHY_MIN_TEMP) / 2)) + +/* + * PHY tuning pattern for calibrating read data capture delay. This 128-by= te + * pattern provides sufficient bit transitions across all byte lanes to + * reliably detect timing windows at high frequencies. + */ +static const u8 phy_tuning_pattern[] __aligned(64) =3D { + 0xFE, 0xFF, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0x00, 0xFE, 0xFE, 0x01, + 0x01, 0x01, 0x01, 0x00, 0x00, 0xFE, 0xFE, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, + 0xFF, 0x00, 0x00, 0xFE, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0xFE, + 0xFE, 0xFF, 0x01, 0x01, 0x01, 0x01, 0x01, 0xFE, 0x00, 0xFE, 0xFE, 0x01, + 0x01, 0x01, 0x01, 0xFE, 0x00, 0xFE, 0xFE, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, + 0xFF, 0xFE, 0x00, 0xFE, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0x00, 0xFE, + 0xFE, 0xFF, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0xFE, 0xFE, 0xFE, 0x01, + 0x01, 0x01, 0x01, 0x00, 0xFE, 0xFE, 0xFE, 0x01, 0xFF, 0xFF, 0xFF, 0xFF, + 0xFF, 0x00, 0xFE, 0xFE, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0xFE, 0xFE, + 0xFE, 0xFF, 0x01, 0x01, 0x01, 0x01, 0x01, 0xFE, 0xFE, 0xFE, 0xFE, 0x01, + 0x01, 0x01, 0x01, 0xFE, 0xFE, 0xFE, 0xFE, 0x01, +}; + static int cqspi_wait_for_bit(const struct cqspi_driver_platdata *ddata, void __iomem *reg, const u32 mask, bool clr, bool busywait) @@ -1555,10 +1637,1687 @@ static bool cqspi_supports_mem_op(struct spi_mem = *mem, return spi_mem_default_supports_op(mem, op); } =20 +static int cqspi_write_pattern_to_cache(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, + struct spi_mem_op *write_op) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + write_op->data.nbytes =3D sizeof(phy_tuning_pattern); + write_op->data.buf.out =3D phy_tuning_pattern; + + ret =3D spi_mem_exec_op(mem, write_op); + if (ret) { + dev_err(dev, "Failed to write PHY pattern to cache: %d\n", ret); + return ret; + } + dev_dbg(dev, "PHY pattern (%zu bytes) written to cache\n", + sizeof(phy_tuning_pattern)); + + return 0; +} + +static int cqspi_get_phy_pattern_offset(struct device *dev, u32 *offset) +{ + struct device_node *np, *flash_np =3D NULL, *part_np; + const __be32 *reg; + int len; + + if (!dev || !dev->of_node) + return -EINVAL; + + for_each_child_of_node(dev->of_node, np) { + if (of_node_name_prefix(np, "flash")) { + flash_np =3D np; + break; + } + } + + if (!flash_np) + return -ENODEV; + + part_np =3D of_parse_phandle(flash_np, "cdns,phy-pattern-partition", 0); + of_node_put(flash_np); + if (!part_np) + return -ENODEV; + + reg =3D of_get_property(part_np, "reg", &len); + if (reg && len >=3D sizeof(__be32)) { + *offset =3D be32_to_cpu(reg[0]); + of_node_put(part_np); + return 0; + } + + of_node_put(part_np); + return -ENOENT; +} + +static int cqspi_phy_check_pattern(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem) +{ + struct spi_mem_op op; + u8 *read_data; + int ret; + + read_data =3D kmalloc_array(ARRAY_SIZE(phy_tuning_pattern), + sizeof(phy_tuning_pattern[0]), GFP_KERNEL); + if (!read_data) + return -ENOMEM; + + op =3D f_pdata->phy_read_op; + op.data.buf.in =3D read_data; + op.data.nbytes =3D sizeof(phy_tuning_pattern); + + ret =3D spi_mem_exec_op(mem, &op); + if (ret) + goto out; + + if (memcmp(read_data, phy_tuning_pattern, sizeof(phy_tuning_pattern))) + ret =3D -EAGAIN; + +out: + kfree(read_data); + return ret; +} + +static void cqspi_phy_set_dll_master(struct cqspi_st *cqspi) +{ + void __iomem *reg_base =3D cqspi->iobase; + unsigned int reg; + + reg =3D readl(reg_base + CQSPI_REG_PHY_DLL_MASTER); + reg &=3D ~((CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_LEN + << CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_LSB) | + CQSPI_REG_PHY_DLL_MASTER_BYPASS | + CQSPI_REG_PHY_DLL_MASTER_CYCLE); + reg |=3D ((CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_3 + << CQSPI_REG_PHY_DLL_MASTER_DLY_ELMTS_LSB) | + CQSPI_REG_PHY_DLL_MASTER_CYCLE); + + writel(reg, reg_base + CQSPI_REG_PHY_DLL_MASTER); +} + +static void cqspi_phy_pre_config(struct cqspi_st *cqspi, + struct cqspi_flash_pdata *f_pdata, + const bool bypass) +{ + void __iomem *reg_base =3D cqspi->iobase; + unsigned int reg; + u8 dummy; + + cqspi_readdata_capture(cqspi, bypass, f_pdata->use_dqs, + f_pdata->phy_setting.read_delay); + + reg =3D readl(reg_base + CQSPI_REG_CONFIG); + reg &=3D ~(CQSPI_REG_CONFIG_PHY_EN | CQSPI_REG_CONFIG_PHY_PIPELINE); + reg |=3D CQSPI_REG_CONFIG_PHY_EN; + writel(reg, reg_base + CQSPI_REG_CONFIG); + + reg =3D readl(reg_base + CQSPI_REG_RD_INSTR); + dummy =3D FIELD_GET(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + reg); + dummy--; + reg &=3D ~(CQSPI_REG_RD_INSTR_DUMMY_MASK << CQSPI_REG_RD_INSTR_DUMMY_LSB); + reg |=3D FIELD_PREP(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + dummy); + writel(reg, reg_base + CQSPI_REG_RD_INSTR); + + cqspi_phy_set_dll_master(cqspi); +} + +static void cqspi_phy_post_config(struct cqspi_st *cqspi, + const unsigned int delay) +{ + void __iomem *reg_base =3D cqspi->iobase; + unsigned int reg; + u8 dummy; + + reg =3D readl(reg_base + CQSPI_REG_READCAPTURE); + reg &=3D ~(CQSPI_REG_READCAPTURE_DELAY_MASK + << CQSPI_REG_READCAPTURE_DELAY_LSB); + + reg |=3D (delay & CQSPI_REG_READCAPTURE_DELAY_MASK) + << CQSPI_REG_READCAPTURE_DELAY_LSB; + writel(reg, reg_base + CQSPI_REG_READCAPTURE); + + reg =3D readl(reg_base + CQSPI_REG_CONFIG); + reg &=3D ~(CQSPI_REG_CONFIG_PHY_EN | CQSPI_REG_CONFIG_PHY_PIPELINE); + writel(reg, reg_base + CQSPI_REG_CONFIG); + + reg =3D readl(reg_base + CQSPI_REG_RD_INSTR); + dummy =3D FIELD_GET(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + reg); + dummy++; + reg &=3D ~(CQSPI_REG_RD_INSTR_DUMMY_MASK << CQSPI_REG_RD_INSTR_DUMMY_LSB); + reg |=3D FIELD_PREP(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + dummy); + writel(reg, reg_base + CQSPI_REG_RD_INSTR); +} + +static void cqspi_set_dll(void __iomem *reg_base, u8 rx_dll, u8 tx_dll) +{ + unsigned int reg; + + reg =3D readl(reg_base + CQSPI_REG_PHY_CONFIG); + reg &=3D ~((CQSPI_REG_PHY_CONFIG_RX_DEL_MASK + << CQSPI_REG_PHY_CONFIG_RX_DEL_LSB) | + (CQSPI_REG_PHY_CONFIG_TX_DEL_MASK + << CQSPI_REG_PHY_CONFIG_TX_DEL_LSB)); + reg |=3D ((rx_dll & CQSPI_REG_PHY_CONFIG_RX_DEL_MASK) + << CQSPI_REG_PHY_CONFIG_RX_DEL_LSB) | + ((tx_dll & CQSPI_REG_PHY_CONFIG_TX_DEL_MASK) + << CQSPI_REG_PHY_CONFIG_TX_DEL_LSB) | + CQSPI_REG_PHY_CONFIG_RESYNC; + writel(reg, reg_base + CQSPI_REG_PHY_CONFIG); +} + +static int cqspi_resync_dll(struct cqspi_st *cqspi) +{ + void __iomem *reg_base =3D cqspi->iobase; + unsigned int reg; + int ret; + + ret =3D cqspi_wait_idle(cqspi); + if (ret) + return ret; + + reg =3D readl(reg_base + CQSPI_REG_CONFIG); + reg &=3D ~CQSPI_REG_CONFIG_ENABLE_MASK; + writel(reg, reg_base + CQSPI_REG_CONFIG); + + reg =3D readl(reg_base + CQSPI_REG_PHY_CONFIG); + reg &=3D ~(CQSPI_REG_PHY_CONFIG_DLL_RESET | CQSPI_REG_PHY_CONFIG_RESYNC); + writel(reg, reg_base + CQSPI_REG_PHY_CONFIG); + + reg =3D readl(reg_base + CQSPI_REG_PHY_DLL_MASTER); + reg |=3D (CQSPI_REG_PHY_DLL_MASTER_INIT_DELAY_VAL + << CQSPI_REG_PHY_DLL_MASTER_INIT_DELAY_LSB); + writel(reg, reg_base + CQSPI_REG_PHY_DLL_MASTER); + + reg =3D readl(reg_base + CQSPI_REG_PHY_CONFIG); + reg |=3D CQSPI_REG_PHY_CONFIG_DLL_RESET; + writel(reg, reg_base + CQSPI_REG_PHY_CONFIG); + + ret =3D readl_poll_timeout(reg_base + CQSPI_REG_DLL_OBS_LOW, reg, + (reg & CQSPI_REG_DLL_OBS_LOW_DLL_LOCK), 0, + CQSPI_DLL_TIMEOUT_US); + if (ret) + goto re_enable; + + ret =3D readl_poll_timeout(reg_base + CQSPI_REG_DLL_OBS_LOW, reg, + (reg & CQSPI_REG_DLL_OBS_LOW_LOOPBACK_LOCK), 0, + CQSPI_DLL_TIMEOUT_US); + if (ret) + goto re_enable; + + reg =3D readl(reg_base + CQSPI_REG_PHY_CONFIG); + reg |=3D CQSPI_REG_PHY_CONFIG_RESYNC; + writel(reg, reg_base + CQSPI_REG_PHY_CONFIG); + +re_enable: + reg =3D readl(reg_base + CQSPI_REG_CONFIG); + reg |=3D CQSPI_REG_CONFIG_ENABLE_MASK; + writel(reg, reg_base + CQSPI_REG_CONFIG); + + return ret; +} + +static int cqspi_phy_apply_setting(struct cqspi_flash_pdata *f_pdata, + struct phy_setting *phy) +{ + struct cqspi_st *cqspi =3D f_pdata->cqspi; + unsigned int reg; + int ret; + + reg =3D readl(cqspi->iobase + CQSPI_REG_READCAPTURE); + reg |=3D BIT(CQSPI_REG_READCAPTURE_EDGE_LSB); + writel(reg, cqspi->iobase + CQSPI_REG_READCAPTURE); + + cqspi_set_dll(cqspi->iobase, phy->rx, phy->tx); + + ret =3D cqspi_resync_dll(cqspi); + if (ret) + return ret; + + f_pdata->phy_setting.read_delay =3D phy->read_delay; + return 0; +} + +static int cqspi_find_rx_low_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, struct phy_setting *phy) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + do { + phy->rx =3D CQSPI_PHY_RX_LOW_SEARCH_START; + do { + ret =3D cqspi_phy_apply_setting(f_pdata, phy); + if (!ret) { + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (!ret) + return 0; + } + + phy->rx +=3D CQSPI_PHY_DDR_SEARCH_STEP; + } while (phy->rx <=3D CQSPI_PHY_RX_LOW_SEARCH_END); + + phy->read_delay++; + } while (phy->read_delay <=3D CQSPI_PHY_MAX_RD); + + dev_dbg(dev, "Unable to find RX low\n"); + return -ENOENT; +} + +static int cqspi_find_rx_low_sdr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, struct phy_setting *phy) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + phy->rx =3D 0; + do { + ret =3D cqspi_phy_apply_setting(f_pdata, phy); + if (!ret) { + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (!ret) + return 0; + } + phy->rx++; + } while (phy->rx <=3D CQSPI_PHY_MAX_DELAY); + + dev_dbg(dev, "Unable to find RX low\n"); + return -ENOENT; +} + +static int cqspi_find_rx_high_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, struct phy_setting *phy) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + do { + phy->rx =3D CQSPI_PHY_RX_HIGH_SEARCH_END; + do { + ret =3D cqspi_phy_apply_setting(f_pdata, phy); + if (!ret) { + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (!ret) + return 0; + } + + phy->rx -=3D CQSPI_PHY_DDR_SEARCH_STEP; + } while (phy->rx >=3D CQSPI_PHY_RX_HIGH_SEARCH_START); + + phy->read_delay--; + } while (phy->read_delay >=3D CQSPI_PHY_INIT_RD); + + dev_dbg(dev, "Unable to find RX high\n"); + return -ENOENT; +} + +static int cqspi_find_rx_high_sdr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, struct phy_setting *phy, + u8 lowerbound) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + phy->rx =3D CQSPI_PHY_MAX_DELAY; + do { + ret =3D cqspi_phy_apply_setting(f_pdata, phy); + if (!ret) { + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (!ret) + return 0; + } + phy->rx--; + } while (phy->rx > lowerbound); + + dev_dbg(dev, "Unable to find RX high\n"); + return -ENOENT; +} + +static int cqspi_find_tx_low_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, struct phy_setting *phy) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + do { + phy->tx =3D CQSPI_PHY_TX_LOW_SEARCH_START; + do { + ret =3D cqspi_phy_apply_setting(f_pdata, phy); + if (!ret) { + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (!ret) + return 0; + } + + phy->tx +=3D CQSPI_PHY_DDR_SEARCH_STEP; + } while (phy->tx <=3D CQSPI_PHY_TX_LOW_SEARCH_END); + + phy->read_delay++; + } while (phy->read_delay <=3D CQSPI_PHY_MAX_RD); + + dev_dbg(dev, "Unable to find TX low\n"); + return -ENOENT; +} + +static int cqspi_find_tx_high_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, struct phy_setting *phy) +{ + struct device *dev =3D &f_pdata->cqspi->pdev->dev; + int ret; + + do { + phy->tx =3D CQSPI_PHY_TX_HIGH_SEARCH_END; + do { + ret =3D cqspi_phy_apply_setting(f_pdata, phy); + if (!ret) { + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (!ret) + return 0; + } + + phy->tx -=3D CQSPI_PHY_DDR_SEARCH_STEP; + } while (phy->tx >=3D CQSPI_PHY_TX_HIGH_SEARCH_START); + + phy->read_delay--; + } while (phy->read_delay >=3D CQSPI_PHY_INIT_RD); + + dev_dbg(dev, "Unable to find TX high\n"); + return -ENOENT; +} + +static void cqspi_phy_find_gaplow_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, + struct phy_setting *bottomleft, + struct phy_setting *topright, + struct phy_setting *gaplow) +{ + struct phy_setting left, right, mid; + int ret; + + left =3D *bottomleft; + right =3D *topright; + + mid.tx =3D left.tx + ((right.tx - left.tx) / 2); + mid.rx =3D left.rx + ((right.rx - left.rx) / 2); + mid.read_delay =3D left.read_delay; + + do { + ret =3D cqspi_phy_apply_setting(f_pdata, &mid); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret) { + /* The pattern was not found. Go to the lower half. */ + right.tx =3D mid.tx; + right.rx =3D mid.rx; + + mid.tx =3D left.tx + ((mid.tx - left.tx) / 2); + mid.rx =3D left.rx + ((mid.rx - left.rx) / 2); + } else { + /* The pattern was found. Go to the upper half. */ + left.tx =3D mid.tx; + left.rx =3D mid.rx; + + mid.tx =3D mid.tx + ((right.tx - mid.tx) / 2); + mid.rx =3D mid.rx + ((right.rx - mid.rx) / 2); + } + + /* Break the loop if the window has closed. */ + } while ((right.tx - left.tx >=3D 2) && (right.rx - left.rx >=3D 2)); + + *gaplow =3D mid; +} + +static void cqspi_phy_find_gaphigh_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem, + struct phy_setting *bottomleft, + struct phy_setting *topright, + struct phy_setting *gaphigh) +{ + struct phy_setting left, right, mid; + int ret; + + left =3D *bottomleft; + right =3D *topright; + + mid.tx =3D left.tx + ((right.tx - left.tx) / 2); + mid.rx =3D left.rx + ((right.rx - left.rx) / 2); + mid.read_delay =3D right.read_delay; + + do { + ret =3D cqspi_phy_apply_setting(f_pdata, &mid); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret) { + /* The pattern was not found. Go to the upper half. */ + left.tx =3D mid.tx; + left.rx =3D mid.rx; + + mid.tx =3D mid.tx + ((right.tx - mid.tx) / 2); + mid.rx =3D mid.rx + ((right.rx - mid.rx) / 2); + } else { + /* The pattern was found. Go to the lower half. */ + right.tx =3D mid.tx; + right.rx =3D mid.rx; + + mid.tx =3D left.tx + ((mid.tx - left.tx) / 2); + mid.rx =3D left.rx + ((mid.rx - left.rx) / 2); + } + + /* Break the loop if the window has closed. */ + } while ((right.tx - left.tx >=3D 2) && (right.rx - left.rx >=3D 2)); + + *gaphigh =3D mid; +} + +static int cqspi_get_temp(int *temp) +{ + /* TODO: read SoC thermal sensor; caller falls back to room temperature */ + return -EOPNOTSUPP; +} + +static inline void cqspi_phy_reset_setting(struct phy_setting *phy) +{ + *phy =3D (struct phy_setting){ .rx =3D 0, .tx =3D 127, .read_delay =3D 0 = }; +} + +static int cqspi_phy_tuning_ddr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem) +{ + struct cqspi_st *cqspi =3D f_pdata->cqspi; + struct device *dev =3D &cqspi->pdev->dev; + struct phy_setting rxlow, rxhigh, txlow, txhigh; + struct phy_setting srxlow, srxhigh; + struct phy_setting bottomleft, topright, searchpoint; + struct phy_setting gaplow, gaphigh; + struct phy_setting backuppoint, backupcornerpoint; + int ret, rx_window, temp; + bool primary =3D true, secondary =3D true; + + /* + * DDR tuning: 2D search across RX and TX delays for optimal timing. + * + * Algorithm: Find RX boundaries (rxlow/rxhigh) using TX window search, + * find TX boundaries (txlow/txhigh) at fixed RX, define valid region, + * locate gaps via binary search, select final point with temperature + * compensation. + * + * rx + * 127 ^ + * | topright + * | * + * | xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * | xxxxxxx ++++++++++++++++++ + * | xxxxxxxx +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++++++++ + * | xxxxxxxxxxxxx ++++++++++++ + * | xxxxxxxxxxxxxx +++++++++++ + * | xxxxxxxxxxxxxxx ++++++++++ + * | xxxxxxxxxxxxxxxx +++++++++ + * | xxxxxxxxxxxxxxxxx ++++++++ + * | xxxxxxxxxxxxxxxxxx +++++++ + * | * + * | bottomleft + * -----------------------------------------> tx + * 0 127 + */ + + f_pdata->use_phy =3D true; + + /* Golden rxlow search: Find lower RX boundary using TX window sweep */ + + /* + * rx + * 127 ^ + * | xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * | xxxxxxx ++++++++++++++++++ + * | xxxxxxxx +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | |xxxxx|xxxxx +++++++++++++ + * | |xxxxx|xxxxxx ++++++++++++ + * search | |xxxxx|xxxxxxx +++++++++++ + * rxlow --------->|xxxxx|xxxxxxxx ++++++++++ + * | |xxxxx|xxxxxxxxx +++++++++ + * | |xxxxx|xxxxxxxxxx ++++++++ + * | |xxxxx|xxxxxxxxxxx +++++++ + * | | | + * --------|-----|----------------------------> tx + * 0 | | 127 + * txlow txlow + * start end + * + * |----------------------------------------------------------| + * | Primary | Secondary | Final | + * | Search | Search | Point | + * |---------|-----------|------------------------------------| + * | Fail | Fail | Return Fail | + * |---------|-----------|------------------------------------| + * | Fail | Pass | Return Fail | + * |---------|-----------|------------------------------------| + * | Pass | Fail | Return Fail | + * |---------|-----------|------------------------------------| + * | Pass | Pass | rx =3D min(primary.rx, secondary.rx) | + * | | | tx =3D primary.tx | + * | | | read_delay =3D | + * | | | min(primary.read_delay, | + * | | | secondary.read_delay) | + * |----------------------------------------------------------| + */ + + /* Primary rxlow: Sweep TX window to find valid RX lower bound */ + + rxlow.tx =3D CQSPI_PHY_TX_LOOKUP_LOW_START; + do { + dev_dbg(dev, "Searching for Golden Primary rxlow on TX =3D %d\n", + rxlow.tx); + rxlow.read_delay =3D CQSPI_PHY_INIT_RD; + ret =3D cqspi_find_rx_low_ddr(f_pdata, mem, &rxlow); + rxlow.tx +=3D CQSPI_PHY_DDR_SEARCH_STEP; + } while (ret && rxlow.tx <=3D CQSPI_PHY_TX_LOOKUP_LOW_END); + if (ret) + goto out; + dev_dbg(dev, "Golden Primary rxlow: RX: %d TX: %d RD: %d\n", rxlow.rx, + rxlow.tx, rxlow.read_delay); + + /* Secondary rxlow: Verify at offset TX for robustness */ + + if (rxlow.tx <=3D (CQSPI_PHY_TX_LOOKUP_LOW_END - CQSPI_PHY_SEARCH_OFFSET)) + srxlow.tx =3D rxlow.tx + CQSPI_PHY_SEARCH_OFFSET; + else + srxlow.tx =3D CQSPI_PHY_TX_LOOKUP_LOW_END; + dev_dbg(dev, "Searching for Golden Secondary rxlow on TX =3D %d\n", + srxlow.tx); + srxlow.read_delay =3D CQSPI_PHY_INIT_RD; + ret =3D cqspi_find_rx_low_ddr(f_pdata, mem, &srxlow); + if (ret) + goto out; + dev_dbg(dev, "Golden Secondary rxlow: RX: %d TX: %d RD: %d\n", + srxlow.rx, srxlow.tx, srxlow.read_delay); + + rxlow.rx =3D min(rxlow.rx, srxlow.rx); + rxlow.read_delay =3D min(rxlow.read_delay, srxlow.read_delay); + dev_dbg(dev, "Golden Final rxlow: RX: %d TX: %d RD: %d\n", rxlow.rx, + rxlow.tx, rxlow.read_delay); + + /* Golden rxhigh search: Find upper RX boundary at fixed TX */ + + /* + * rx + * 127 ^ + * | |xxxx ++++++++++++++++++++ + * | |xxxxx +++++++++++++++++++ + * search | |xxxxxx ++++++++++++++++++ + * rxhigh --------->|xxxxxxx +++++++++++++++++ + * on fixed | |xxxxxxxx ++++++++++++++++ + * tx | |xxxxxxxxx +++++++++++++++ + * | |xxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++++++++ + * | xxxxxxxxxxxxx ++++++++++++ + * | xxxxxxxxxxxxxx +++++++++++ + * | xxxxxxxxxxxxxxx ++++++++++ + * | xxxxxxxxxxxxxxxx +++++++++ + * | xxxxxxxxxxxxxxxxx ++++++++ + * | xxxxxxxxxxxxxxxxxx +++++++ + * | + * -------------------------------------------> tx + * 0 127 + * + * |----------------------------------------------------------| + * | Primary | Secondary | Final | + * | Search | Search | Point | + * |---------|-----------|------------------------------------| + * | Fail | Fail | Return Fail | + * |---------|-----------|------------------------------------| + * | Fail | Pass | Choose Secondary | + * |---------|-----------|------------------------------------| + * | Pass | Fail | Choose Primary | + * |---------|-----------|------------------------------------| + * | Pass | Pass | if (secondary.rx > primary.rx) | + * | | | Choose Secondary | + * | | | else | + * | | | Choose Primary | + * |----------------------------------------------------------| + */ + + /* Primary rxhigh: Search at rxlow's TX, decrement from max read_delay */ + + rxhigh.tx =3D rxlow.tx; + dev_dbg(dev, "Searching for Golden Primary rxhigh on TX =3D %d\n", + rxhigh.tx); + rxhigh.read_delay =3D CQSPI_PHY_MAX_RD; + ret =3D cqspi_find_rx_high_ddr(f_pdata, mem, &rxhigh); + if (ret) + primary =3D false; + dev_dbg(dev, "Golden Primary rxhigh: RX: %d TX: %d RD: %d\n", rxhigh.rx, + rxhigh.tx, rxhigh.read_delay); + + /* Secondary rxhigh: Verify at offset TX */ + + if (rxhigh.tx <=3D + (CQSPI_PHY_TX_LOOKUP_LOW_END - CQSPI_PHY_SEARCH_OFFSET)) + srxhigh.tx =3D rxhigh.tx + CQSPI_PHY_SEARCH_OFFSET; + else + srxhigh.tx =3D CQSPI_PHY_TX_LOOKUP_LOW_END; + dev_dbg(dev, "Searching for Golden Secondary rxhigh on TX =3D %d\n", + srxhigh.tx); + srxhigh.read_delay =3D CQSPI_PHY_MAX_RD; + ret =3D cqspi_find_rx_high_ddr(f_pdata, mem, &srxhigh); + if (ret) + secondary =3D false; + dev_dbg(dev, "Golden Secondary rxhigh: RX: %d TX: %d RD: %d\n", + srxhigh.rx, srxhigh.tx, srxhigh.read_delay); + + if (!primary && !secondary) + goto out; + else if (!primary) + rxhigh =3D srxhigh; + else if (secondary && srxhigh.rx > rxhigh.rx) + rxhigh =3D srxhigh; + dev_dbg(dev, "Golden Final rxhigh: RX: %d TX: %d RD: %d\n", rxhigh.rx, + rxhigh.tx, rxhigh.read_delay); + + primary =3D true; + secondary =3D true; + + /* If rxlow/rxhigh at same read_delay, search backup at upper TX range */ + + if (rxlow.read_delay =3D=3D rxhigh.read_delay) { + dev_dbg(dev, "rxlow and rxhigh at the same read delay.\n"); + + /* Backup rxlow: Search at high TX window */ + + /* + * rx + * 127 ^ + * | xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * | xxxxxxx ++++++++++++++++++ + * | xxxxxxxx +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++|++++| + * | xxxxxxxxxxxxx ++++++|++++| + * search | xxxxxxxxxxxxxx +++++|++++| + * rxlow --------------------------------->|++++| + * | xxxxxxxxxxxxxxxx +++|++++| + * | xxxxxxxxxxxxxxxxx ++|++++| + * | xxxxxxxxxxxxxxxxxx +|++++| + * | | | + * --------------------------------|----|-----> tx + * 0 | | 127 + * txhigh txhigh + * start end + * + * |-----------------------------------------------------| + * | Primary | Secondary | Final | + * | Search | Search | Point | + * |---------|-----------|-------------------------------| + * | Fail | Fail | Return Fail | + * |---------|-----------|-------------------------------| + * | Fail | Pass | Return Fail | + * |---------|-----------|-------------------------------| + * | Pass | Fail | Return Fail | + * |---------|-----------|-------------------------------| + * | Pass | Pass | rx =3D | + * | | | min(primary.rx, secondary.rx)| + * | | | tx =3D primary.tx | + * | | | read_delay =3D | + * | | | min(primary.read_delay, | + * | | | secondary.read_delay) | + * |-----------------------------------------------------| + */ + + /* Primary backup: Decrement TX from high window end */ + + backuppoint.tx =3D CQSPI_PHY_TX_LOOKUP_HIGH_END; + do { + dev_dbg(dev, + "Searching for Backup Primary rxlow on TX =3D %d\n", + backuppoint.tx); + backuppoint.read_delay =3D CQSPI_PHY_INIT_RD; + ret =3D cqspi_find_rx_low_ddr(f_pdata, mem, &backuppoint); + backuppoint.tx -=3D CQSPI_PHY_DDR_SEARCH_STEP; + } while (ret && + backuppoint.tx >=3D CQSPI_PHY_TX_LOOKUP_HIGH_START); + if (ret) + goto out; + dev_dbg(dev, "Backup Primary rxlow: RX: %d TX: %d RD: %d\n", + backuppoint.rx, backuppoint.tx, backuppoint.read_delay); + + /* Secondary backup: Verify at offset TX */ + + if (backuppoint.tx >=3D + (CQSPI_PHY_TX_LOOKUP_HIGH_START + CQSPI_PHY_SEARCH_OFFSET)) + srxlow.tx =3D backuppoint.tx - CQSPI_PHY_SEARCH_OFFSET; + else + srxlow.tx =3D CQSPI_PHY_TX_LOOKUP_HIGH_START; + dev_dbg(dev, + "Searching for Backup Secondary rxlow on TX =3D %d\n", + srxlow.tx); + srxlow.read_delay =3D CQSPI_PHY_INIT_RD; + ret =3D cqspi_find_rx_low_ddr(f_pdata, mem, &srxlow); + if (ret) + goto out; + dev_dbg(dev, "Backup Secondary rxlow: RX: %d TX: %d RD: %d\n", + srxlow.rx, srxlow.tx, srxlow.read_delay); + + backuppoint.rx =3D min(backuppoint.rx, srxlow.rx); + backuppoint.read_delay =3D + min(backuppoint.read_delay, srxlow.read_delay); + dev_dbg(dev, "Backup Final rxlow: RX: %d TX: %d RD: %d\n", + backuppoint.rx, backuppoint.tx, backuppoint.read_delay); + + if (backuppoint.rx < rxlow.rx) { + rxlow =3D backuppoint; + dev_dbg(dev, "Updating rxlow to the one at TX =3D %d\n", + backuppoint.tx); + } + dev_dbg(dev, "Final rxlow: RX: %d TX: %d RD: %d\n", rxlow.rx, + rxlow.tx, rxlow.read_delay); + + /* Backup rxhigh: Search at fixed backup TX */ + + /* + * rx + * 127 ^ + * | xxxxx +++++++++++++++++++| + * | xxxxxx ++++++++++++++++++| + * search | xxxxxxx +++++++++++++++++| + * rxhigh -------------------------------------->| + * on fixed | xxxxxxxxx +++++++++++++++| + * tx | xxxxxxxxxx ++++++++++++++| + * | xxxxxxxxxxx +++++++++++++| + * | xxxxxxxxxxxx +++++++++++++ + * | xxxxxxxxxxxxx ++++++++++++ + * | xxxxxxxxxxxxxx +++++++++++ + * | xxxxxxxxxxxxxxx ++++++++++ + * | xxxxxxxxxxxxxxxx +++++++++ + * | xxxxxxxxxxxxxxxxx ++++++++ + * | xxxxxxxxxxxxxxxxxx +++++++ + * | + * -------------------------------------------> tx + * 0 127 + * + * |-----------------------------------------------------| + * | Primary | Secondary | Final | + * | Search | Search | Point | + * |---------|-----------|-------------------------------| + * | Fail | Fail | Return Fail | + * |---------|-----------|-------------------------------| + * | Fail | Pass | Choose Secondary | + * |---------|-----------|-------------------------------| + * | Pass | Fail | Choose Primary | + * |---------|-----------|-------------------------------| + * | Pass | Pass | if (secondary.rx > primary.rx)| + * | | | Choose Secondary | + * | | | else | + * | | | Choose Primary | + * |-----------------------------------------------------| + */ + + /* Primary backup rxhigh: Use backup TX, decrement from max read_delay */ + + dev_dbg(dev, "Searching for Backup Primary rxhigh on TX =3D %d\n", + backuppoint.tx); + backuppoint.read_delay =3D CQSPI_PHY_MAX_RD; + ret =3D cqspi_find_rx_high_ddr(f_pdata, mem, &backuppoint); + if (ret) + primary =3D false; + dev_dbg(dev, "Backup Primary rxhigh: RX: %d TX: %d RD: %d\n", + backuppoint.rx, backuppoint.tx, backuppoint.read_delay); + + /* Secondary backup rxhigh: Verify at offset TX */ + + if (backuppoint.tx >=3D + (CQSPI_PHY_TX_LOOKUP_HIGH_START + CQSPI_PHY_SEARCH_OFFSET)) + srxhigh.tx =3D backuppoint.tx - CQSPI_PHY_SEARCH_OFFSET; + else + srxhigh.tx =3D CQSPI_PHY_TX_LOOKUP_HIGH_START; + dev_dbg(dev, + "Searching for Backup Secondary rxhigh on TX =3D %d\n", + srxhigh.tx); + srxhigh.read_delay =3D CQSPI_PHY_MAX_RD; + ret =3D cqspi_find_rx_high_ddr(f_pdata, mem, &srxhigh); + if (ret) + secondary =3D false; + dev_dbg(dev, "Backup Secondary rxhigh: RX: %d TX: %d RD: %d\n", + srxhigh.rx, srxhigh.tx, srxhigh.read_delay); + + if (!primary && !secondary) + goto out; + else if (!primary) + backuppoint =3D srxhigh; + else if (secondary && srxhigh.rx > backuppoint.rx) + backuppoint =3D srxhigh; + dev_dbg(dev, "Backup Final rxhigh: RX: %d TX: %d RD: %d\n", + backuppoint.rx, backuppoint.tx, backuppoint.read_delay); + + if (backuppoint.rx > rxhigh.rx) { + rxhigh =3D backuppoint; + dev_dbg(dev, "Updating rxhigh to the one at TX =3D %d\n", + backuppoint.tx); + } + dev_dbg(dev, "Final rxhigh: RX: %d TX: %d RD: %d\n", rxhigh.rx, + rxhigh.tx, rxhigh.read_delay); + } + + /* Golden txlow: Fix RX at 1/4 of RX window, search TX lower bound */ + + /* + * rx + * 127 ^ + * | + * rxhigh --------->xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * | xxxxxxx ++++++++++++++++++ + * | xxxxxxxx +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++++++++ + * fix rx | xxxxxxxxxxxxx ++++++++++++ + * 1/4 b/w ---------><------->xxxxx +++++++++++ + * rxlow and | xxxx|xxxxxxxxxx ++++++++++ + * rxhigh | xxxx|xxxxxxxxxxx +++++++++ + * | xxxx|xxxxxxxxxxxx ++++++++ + * rxlow --------->xxxx|xxxxxxxxxxxxx +++++++ + * | | + * ------------|------------------------------> tx + * 0 | 127 + * search + * txlow + */ + + rx_window =3D rxhigh.rx - rxlow.rx; + txlow.rx =3D rxlow.rx + (rx_window / 4); + dev_dbg(dev, "Searching for Golden txlow on RX =3D %d\n", txlow.rx); + txlow.read_delay =3D CQSPI_PHY_INIT_RD; + ret =3D cqspi_find_tx_low_ddr(f_pdata, mem, &txlow); + if (ret) + goto out; + dev_dbg(dev, "Golden txlow: RX: %d TX: %d RD: %d\n", txlow.rx, txlow.tx, + txlow.read_delay); + + /* Golden txhigh: Same RX as txlow, decrement from max read_delay */ + + /* + * rx + * 127 ^ + * | + * rxhigh --------->xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * | xxxxxxx ++++++++++++++++++ + * | xxxxxxxx +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++++++++ + * fix rx | xxxxxxxxxxxxx ++++++++++++ + * 1/4 b/w --------------------------------><-----> + * rxlow and | xxxxxxxxxxxxxxx ++++++|+++ + * rxhigh | xxxxxxxxxxxxxxxx +++++|+++ + * | xxxxxxxxxxxxxxxxx ++++|+++ + * rxlow --------->xxxxxxxxxxxxxxxxxx +++|+++ + * | | + * ----------------------------------|--------> tx + * 0 | 127 + * search + * txhigh + */ + + txhigh.rx =3D txlow.rx; + dev_dbg(dev, "Searching for Golden txhigh on RX =3D %d\n", txhigh.rx); + txhigh.read_delay =3D CQSPI_PHY_MAX_RD; + ret =3D cqspi_find_tx_high_ddr(f_pdata, mem, &txhigh); + if (ret) + goto out; + dev_dbg(dev, "Golden txhigh: RX: %d TX: %d RD: %d\n", txhigh.rx, + txhigh.tx, txhigh.read_delay); + + /* If txlow/txhigh at same read_delay, search backup at 3/4 RX window */ + + if (txlow.read_delay =3D=3D txhigh.read_delay) { + /* Backup txlow: Fix RX at 3/4 of RX window */ + + /* + * rx + * 127 ^ + * | + * rxhigh --------->xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * fix rx | xxxxxxx ++++++++++++++++++ + * 3/4 b/w ---------><----->x +++++++++++++++++ + * rxlow and | xxxx|xxxx ++++++++++++++++ + * rxhigh | xxxx|xxxxx +++++++++++++++ + * | xxxx|xxxxxx ++++++++++++++ + * | xxxx|xxxxxxx +++++++++++++ + * | xxxx|xxxxxxxx ++++++++++++ + * | xxxx|xxxxxxxxx +++++++++++ + * | xxxx|xxxxxxxxxx ++++++++++ + * | xxxx|xxxxxxxxxxx +++++++++ + * | xxxx|xxxxxxxxxxxx ++++++++ + * rxlow --------->xxxx|xxxxxxxxxxxxx +++++++ + * | | + * ------------|------------------------------> tx + * 0 | 127 + * search + * txlow + */ + + dev_dbg(dev, "txlow and txhigh at the same read delay.\n"); + backuppoint.rx =3D rxlow.rx + ((rx_window * 3) / 4); + dev_dbg(dev, "Searching for Backup txlow on RX =3D %d\n", + backuppoint.rx); + backuppoint.read_delay =3D CQSPI_PHY_INIT_RD; + ret =3D cqspi_find_tx_low_ddr(f_pdata, mem, &backuppoint); + if (ret) + goto out; + dev_dbg(dev, "Backup txlow: RX: %d TX: %d RD: %d\n", + backuppoint.rx, backuppoint.tx, backuppoint.read_delay); + + if (backuppoint.tx < txlow.tx) { + txlow =3D backuppoint; + dev_dbg(dev, "Updating txlow with the one at RX =3D %d\n", + backuppoint.rx); + } + dev_dbg(dev, "Final txlow: RX: %d TX: %d RD: %d\n", txlow.rx, + txlow.tx, txlow.read_delay); + + /* Backup txhigh: Same RX as backup txlow, decrement from max */ + + /* + * rx + * 127 ^ + * | + * rxhigh --------->xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * fix rx | xxxxxxx ++++++++++++++++++ + * 3/4 b/w ------------------------------><-------> + * rxlow and | xxxxxxxxx +++++++++++|++++ + * rxhigh | xxxxxxxxxx ++++++++++|++++ + * | xxxxxxxxxxx +++++++++|++++ + * | xxxxxxxxxxxx ++++++++|++++ + * | xxxxxxxxxxxxx +++++++|++++ + * | xxxxxxxxxxxxxx ++++++|++++ + * | xxxxxxxxxxxxxxx +++++|++++ + * | xxxxxxxxxxxxxxxx ++++|++++ + * | xxxxxxxxxxxxxxxxx +++|++++ + * rxlow --------->xxxxxxxxxxxxxxxxxx ++|++++ + * | | + * ---------------------------------|---------> tx + * 0 | 127 + * search + * txhigh + */ + + dev_dbg(dev, "Searching for Backup txhigh on RX =3D %d\n", + backuppoint.rx); + backuppoint.read_delay =3D CQSPI_PHY_MAX_RD; + ret =3D cqspi_find_tx_high_ddr(f_pdata, mem, &backuppoint); + if (ret) + goto out; + dev_dbg(dev, "Backup txhigh: RX: %d TX: %d RD: %d\n", + backuppoint.rx, backuppoint.tx, backuppoint.read_delay); + + if (backuppoint.tx > txhigh.tx) { + txhigh =3D backuppoint; + dev_dbg(dev, + "Updating txhigh with the one at RX =3D %d\n", + backuppoint.rx); + } + dev_dbg(dev, "Final txhigh: RX: %d TX: %d RD: %d\n", txhigh.rx, + txhigh.tx, txhigh.read_delay); + } + + /* Corner points: Define and verify bottomleft and topright boundaries */ + + /* + * rx + * 127 ^ + * | topright + * | * + * rxhigh -----------xxxxx ++++++++++++++++++++ + * | xxxxxx +++++++++++++++++++ + * | xxxxxxx ++++++++++++++++++ + * | xxxxxxxx +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++++++++ + * | xxxxxxxxxxxxx ++++++++++++ + * | xxxxxxxxxxxxxx +++++++++++ + * | xxxxxxxxxxxxxxx ++++++++++ + * | xxxxxxxxxxxxxxxx +++++++++ + * | xxxxxxxxxxxxxxxxx ++++++++ + * rxlow -----------xxxxxxxxxxxxxxxxxx +++++++ + * | * | + * | bottom|left | + * --------|----------------------------|---> tx + * 0 | | 127 + * | | + * txlow txhigh + * + * Verification: Test point 4 taps inside each corner, adjust + * read_delay =C2=B11 if needed to ensure valid corners for gap search. + */ + + bottomleft.tx =3D txlow.tx; + bottomleft.rx =3D rxlow.rx; + if (txlow.read_delay <=3D rxlow.read_delay) + bottomleft.read_delay =3D txlow.read_delay; + else + bottomleft.read_delay =3D rxlow.read_delay; + + /* Verify bottomleft: Test 4 taps inside, adjust read_delay if needed */ + backupcornerpoint =3D bottomleft; + backupcornerpoint.tx +=3D 4; + backupcornerpoint.rx +=3D 4; + ret =3D cqspi_phy_apply_setting(f_pdata, &backupcornerpoint); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret) { + backupcornerpoint.read_delay--; + ret =3D cqspi_phy_apply_setting(f_pdata, &backupcornerpoint); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + } + + if (ret) + goto out; + + bottomleft.read_delay =3D backupcornerpoint.read_delay; + + topright.tx =3D txhigh.tx; + topright.rx =3D rxhigh.rx; + if (txhigh.read_delay >=3D rxhigh.read_delay) + topright.read_delay =3D txhigh.read_delay; + else + topright.read_delay =3D rxhigh.read_delay; + + /* Verify topright: Test 4 taps inside, adjust read_delay if needed */ + backupcornerpoint =3D topright; + backupcornerpoint.tx -=3D 4; + backupcornerpoint.rx -=3D 4; + ret =3D cqspi_phy_apply_setting(f_pdata, &backupcornerpoint); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret) { + backupcornerpoint.read_delay++; + ret =3D cqspi_phy_apply_setting(f_pdata, &backupcornerpoint); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + } + + if (ret) + goto out; + + topright.read_delay =3D backupcornerpoint.read_delay; + + dev_dbg(dev, "topright: RX: %d TX: %d RD: %d\n", topright.rx, + topright.tx, topright.read_delay); + dev_dbg(dev, "bottomleft: RX: %d TX: %d RD: %d\n", bottomleft.rx, + bottomleft.tx, bottomleft.read_delay); + cqspi_phy_find_gaplow_ddr(f_pdata, mem, &bottomleft, &topright, &gaplow); + dev_dbg(dev, "gaplow: RX: %d TX: %d RD: %d\n", gaplow.rx, gaplow.tx, + gaplow.read_delay); + + /* Final point selection: Handle single vs dual passing regions */ + + if (bottomleft.read_delay =3D=3D topright.read_delay) { + /* + * Single region: Use midpoint with temperature compensation. + * Gaplow approximates upper boundary of valid region. + * + * rx + * 127 ^ + * | gaplow (approx. topright) + * | | + * rxhigh -----------xxxxxxx| failing + * | xxxxxxx| region + * | xxxxxxx| <---------------> + * | xxxxxxx| +++++++++++++++++ + * | xxxxxxxxx ++++++++++++++++ + * | xxxxxxxxxx +++++++++++++++ + * | xxxxxxxxxxx ++++++++++++++ + * | xxxxxxxxxxxx +++++++++++++ + * | xxxxxxxxxxxxx ++++++++++++ + * | xxxxxxxxxxxxxx +++++++++++ + * | xxxxxxxxxxxxxxx ++++++++++ + * | xxxxxxxxxxxxxxxx +++++++++ + * | xxxxxxxxxxxxxxxxx ++++++++ + * rxlow -----------xxxxxxxxxxxxxxxxxx +++++++ + * | * | + * | bottom|left | + * --------|----------------------------|---> tx + * 0 | | 127 + * | | + * txlow txhigh + * (same read_delay) + * + * Temperature compensation: Valid region shifts with temp. + * Offset =3D region_size / (330 / (temp - 42=C2=B0C)) + * Factor 330 is empirically determined for this hardware. + */ + + dev_dbg(dev, + "bottomleft and topright at the same read delay.\n"); + + topright =3D gaplow; + searchpoint.read_delay =3D bottomleft.read_delay; + searchpoint.tx =3D + bottomleft.tx + ((topright.tx - bottomleft.tx) / 2); + searchpoint.rx =3D + bottomleft.rx + ((topright.rx - bottomleft.rx) / 2); + + ret =3D cqspi_get_temp(&temp); + if (ret) { + /* Assume room temperature if sensor unavailable */ + dev_dbg(dev, + "Unable to get temperature. Assuming room temperature\n"); + temp =3D CQSPI_PHY_DEFAULT_TEMP; + } + + if (temp < CQSPI_PHY_MIN_TEMP || temp > CQSPI_PHY_MAX_TEMP) { + dev_err(dev, + "Temperature outside operating range: %dC\n", + temp); + ret =3D -EINVAL; + goto out; + } + + if (temp =3D=3D CQSPI_PHY_MID_TEMP) + temp++; /* Avoid divide-by-zero */ + dev_dbg(dev, "Temperature: %dC\n", temp); + + /* + * Apply temperature offset: positive at high temp, negative at low. + * Compute the divisor once and apply to both TX and RX. Use int + * arithmetic throughout to avoid u8 wrapping on negative offsets. + */ + temp =3D 330 / (temp - CQSPI_PHY_MID_TEMP); + searchpoint.tx =3D clamp((int)searchpoint.tx + + (topright.tx - bottomleft.tx) / temp, + 0, CQSPI_PHY_MAX_DELAY); + searchpoint.rx =3D clamp((int)searchpoint.rx + + (topright.rx - bottomleft.rx) / temp, + 0, CQSPI_PHY_MAX_DELAY); + } else { + /* + * Dual regions: Gap separates two valid regions, choose larger. + * + * rx + * 127 ^ + * | topright + * | * + * rxhigh -----------xxxxx +++++++++++++++++++| + * | xxxxxx ++++++++| + * | xxxxxxx +++++++++++++++++| + * | xxxxxxxx ++++++++++++++++| + * | xxxxxxxxx +++++++++++++++| + * | xxxxxxxxxx ++++++++++++++| + * | failing | + * | region | + * | xxxxxxxxxxxxx +++++++++++| + * | xxxxxxxxxxxxxx ++++++++++| + * | xxxxxxxxxxxxxxx +++++++++| + * | xxxxxxxxxxxxxxxx ++++++++| + * | xxxxxxxxx +++++++| + * rxlow -----------xxxxxxxxxxxxxxxxxx ++++++| + * | * | + * | bottom|left | + * --------|----------------------------|---> tx + * 0 | | 127 + * | | + * txlow txhigh + * + * Strategy: Compare Manhattan distances from gap boundaries to + * corners. Choose corner furthest from gap (larger region). + * Apply 16-tap margin inward, scale RX proportionally. + */ + + cqspi_phy_find_gaphigh_ddr(f_pdata, mem, &bottomleft, + &topright, &gaphigh); + dev_dbg(dev, "gaphigh: RX: %d TX: %d RD: %d\n", gaphigh.rx, + gaphigh.tx, gaphigh.read_delay); + + if (topright.tx =3D=3D bottomleft.tx) { + dev_err(dev, "zero TX span in dual-region: cannot compute search point\= n"); + ret =3D -EINVAL; + goto out; + } + + /* Compare Manhattan distances: choose corner furthest from gap */ + if ((abs(gaplow.tx - bottomleft.tx) + + abs(gaplow.rx - bottomleft.rx)) < + (abs(gaphigh.tx - topright.tx) + + abs(gaphigh.rx - topright.rx))) { + /* Topright further: Use Region 2, 16 taps inward */ + searchpoint =3D topright; + searchpoint.tx -=3D 16; + searchpoint.rx -=3D (16 * (topright.rx - bottomleft.rx)) / + (topright.tx - bottomleft.tx); + } else { + /* Bottomleft further: Use Region 1, 16 taps inward */ + searchpoint =3D bottomleft; + searchpoint.tx +=3D 16; + searchpoint.rx +=3D (16 * (topright.rx - bottomleft.rx)) / + (topright.tx - bottomleft.tx); + } + } + + /* Apply and verify final tuning point */ + dev_dbg(dev, "Final tuning point: RX: %d TX: %d RD: %d\n", + searchpoint.rx, searchpoint.tx, searchpoint.read_delay); + ret =3D cqspi_phy_apply_setting(f_pdata, &searchpoint); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret) { + dev_err(dev, + "Failed to find pattern at final calibration point\n"); + ret =3D -EINVAL; + goto out; + } + + f_pdata->phy_setting.read_delay =3D searchpoint.read_delay; + f_pdata->phy_setting.rx =3D searchpoint.rx; + f_pdata->phy_setting.tx =3D searchpoint.tx; +out: + if (ret) + f_pdata->use_phy =3D false; + + return ret; +} + +static int cqspi_phy_tuning_sdr(struct cqspi_flash_pdata *f_pdata, + struct spi_mem *mem) +{ + struct cqspi_st *cqspi =3D f_pdata->cqspi; + struct device *dev =3D &cqspi->pdev->dev; + struct phy_setting rxlow, rxhigh, first, second, final; + u8 window1 =3D 0; + u8 window2 =3D 0; + int ret; + + /* + * SDR tuning: 1D search for optimal RX delay (TX less critical). + * Find two consecutive windows, choose larger, use midpoint. + * + * rx + * 127 ^ + * | |-----window at----------| + * | |-----read_delay =3D n+1---| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | rxlow(n+1) midpoint rxhigh(n+1) + * | + * | |---window at--------| + * | |---read_delay =3D n---| + * | |xxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxx| + * | rxlow(n) midpoint rxhigh(n) + * | + * -----------------------------------------> tx + * 0 127 + * read_delay=3Dn read_delay=3Dn+1 + */ + + f_pdata->use_phy =3D true; + cqspi_phy_reset_setting(&rxlow); + cqspi_phy_reset_setting(&rxhigh); + cqspi_phy_reset_setting(&first); + + /* First window: Find rxlow by incrementing read_delay from 0 */ + + /* + * rx + * 127 ^ + * | |xxxxxxxxxxxxxxxxxxxx| + * search | |xxxxxxxxxxxxxxxxxxxx| + * rxlow | |xxxxxxxxxxxxxxxxxxxx| + * increasing | |xxxxxxxxxxxxxxxxxxxx| + * --------->|xxxxxxxxxxxxxxxxxxxx| + * read_delay | |xxxxxxxxxxxxxxxxxxx| + * until found | |xxxxxxxxxxxxxxxxxxx| + * | rxlow + * -----------------------------------------> tx + * 0 tx fixed at 127 + */ + + do { + ret =3D cqspi_find_rx_low_sdr(f_pdata, mem, &rxlow); + + if (ret) + rxlow.read_delay++; + } while (ret && rxlow.read_delay <=3D CQSPI_PHY_MAX_RD); + + /* Find rxhigh: Decrement from RX=3D127 at same read_delay */ + + /* + * rx + * 127 ^ search rxhigh + * | (decrement from + * | 127 until found) + * | | + * | | + * | v + * | |------------------------| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | rxlow rxhigh + * -----------------------------------------> tx + * 0 tx fixed at 127 + */ + + rxhigh.read_delay =3D rxlow.read_delay; + ret =3D cqspi_find_rx_high_sdr(f_pdata, mem, &rxhigh, rxlow.rx); + if (ret) + goto out; + + /* Calculate first window midpoint for max margin */ + + /* + * rx + * 127 ^ + * | |--------window1---------| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxx * xxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | rxlow ^ rxhigh + * ----------------------|------------------> tx + * 0 | tx fixed at 127 + * window1/2 + */ + + first.read_delay =3D rxlow.read_delay; + window1 =3D rxhigh.rx - rxlow.rx; + first.rx =3D rxlow.rx + (window1 / 2); + + dev_dbg(dev, "First tuning point: RX: %d TX: %d RD: %d\n", first.rx, + first.tx, first.read_delay); + ret =3D cqspi_phy_apply_setting(f_pdata, &first); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret || first.read_delay > CQSPI_PHY_MAX_RD) + goto out; + + /* Second window: Search at read_delay+1, may differ in size */ + + /* + * rx + * 127 ^ + * | |-------| + * | |xxxxxxx| + * | |xxxxxxx| + * | |xxxxxxx| + * | |xxxxxxx| + * | |xxxxxxx| + * | rxlow rxhigh + * -----------------------------------------> tx + * 0 + * read_delay =3D n (smaller window) + * + * rx + * 127 ^ + * | |-----------------| + * | |xxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxx| + * | rxlow rxhigh + * -----------------------------------------> tx + * 0 + * read_delay =3D n+1 (larger window - better) + */ + + cqspi_phy_reset_setting(&rxlow); + cqspi_phy_reset_setting(&rxhigh); + cqspi_phy_reset_setting(&second); + + rxlow.read_delay =3D first.read_delay + 1; + if (rxlow.read_delay > CQSPI_PHY_MAX_RD) + goto compare; + + ret =3D cqspi_find_rx_low_sdr(f_pdata, mem, &rxlow); + if (ret) + goto compare; + + rxhigh.read_delay =3D rxlow.read_delay; + ret =3D cqspi_find_rx_high_sdr(f_pdata, mem, &rxhigh, rxlow.rx); + if (ret) + goto compare; + + /* Calculate second window midpoint */ + + /* + * rx + * 127 ^ + * | |--------window2---------| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxx * xxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | |xxxxxxxxxxxxxxxxxxxxxxxx| + * | rxlow ^ rxhigh + * ----------------------|------------------> tx + * 0 | tx fixed at 127 + * window2/2 + * read_delay =3D n+1 + */ + + window2 =3D rxhigh.rx - rxlow.rx; + second.rx =3D rxlow.rx + (window2 / 2); + second.read_delay =3D rxlow.read_delay; + + dev_dbg(dev, "Second tuning point: RX: %d TX: %d RD: %d\n", second.rx, + second.tx, second.read_delay); + ret =3D cqspi_phy_apply_setting(f_pdata, &second); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret || second.read_delay > CQSPI_PHY_MAX_RD) + window2 =3D 0; + + /* Window comparison: Choose larger window for better margin */ + +compare: + cqspi_phy_reset_setting(&final); + if (window2 > window1) { + final.rx =3D second.rx; + final.read_delay =3D second.read_delay; + } else { + final.rx =3D first.rx; + final.read_delay =3D first.read_delay; + } + + /* Apply and verify final tuning point */ + + dev_dbg(dev, "Final tuning point: RX: %d TX: %d RD: %d\n", final.rx, + final.tx, final.read_delay); + ret =3D cqspi_phy_apply_setting(f_pdata, &final); + if (!ret) + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + + if (ret) { + ret =3D -EINVAL; + goto out; + } + + f_pdata->phy_setting.read_delay =3D final.read_delay; + f_pdata->phy_setting.rx =3D final.rx; + f_pdata->phy_setting.tx =3D final.tx; + +out: + if (ret) + f_pdata->use_phy =3D false; + + return ret; +} + +static int cqspi_am654_ospi_execute_tuning(struct spi_mem *mem, + struct spi_mem_op *read_op, + struct spi_mem_op *write_op) +{ + struct cqspi_st *cqspi =3D + spi_controller_get_devdata(mem->spi->controller); + struct cqspi_flash_pdata *f_pdata; + struct device *dev =3D &cqspi->pdev->dev; + u32 base_speed; + u32 phy_offset =3D 0; + int ret; + + f_pdata =3D &cqspi->f_pdata[spi_get_chipselect(mem->spi, 0)]; + + /* + * A second spi-max-frequency value (the higher clock rate) must be + * present for tiered speed support. Without it there is nothing to + * calibrate towards, so skip tuning gracefully. + */ + if (!f_pdata->max_clk_rate) { + dev_dbg(dev, "No higher clock rate configured, skipping tuning\n"); + return 0; + } + + base_speed =3D mem->spi->base_speed_hz; + + if (write_op) { + /* + * For NAND: write the calibration pattern to the page cache. + * This uses write_op at the safe base speed (base_speed_hz is + * still active) so the write itself is reliable. + */ + ret =3D cqspi_write_pattern_to_cache(f_pdata, mem, write_op); + if (ret) { + dev_warn(dev, + "failed to write pattern to cache: %d, skipping tuning\n", + ret); + goto out; + } + + f_pdata->phy_write_op =3D *write_op; + } else { + ret =3D cqspi_get_phy_pattern_offset(dev, &phy_offset); + if (ret) { + dev_warn(dev, + "pattern partition not found: %d, skipping tuning\n", + ret); + goto out; + } + + read_op->addr.val =3D phy_offset; + } + + /* + * Verify the calibration pattern exists using the conservative base + * speed. At high clock rates the DLL is not yet trained, so DTR + * data capture is unreliable and the read would return garbage. + * Setting max_freq to 0 here causes apply_base_freq_cap() to cap the + * read to base_speed_hz, which is well within reliable DTR margins. + * max_freq is restored to max_speed_hz for the tuning-loop reads + * after base_speed_hz is cleared below. + */ + f_pdata->phy_read_op =3D *read_op; + f_pdata->phy_read_op.max_freq =3D 0; + + ret =3D cqspi_phy_check_pattern(f_pdata, mem); + if (ret) { + dev_err(dev, "pattern not found: %d, skipping tuning\n", ret); + goto out; + } + + /* + * Pattern confirmed. Now clear base_speed_hz so that tuning-loop + * exec_op calls run at max_speed_hz, and restore phy_read_op.max_freq + * so those reads also use the full speed. + */ + mem->spi->base_speed_hz =3D 0; + f_pdata->phy_read_op.max_freq =3D mem->spi->max_speed_hz; + + if (read_op->cmd.dtr || read_op->addr.dtr || read_op->dummy.dtr || + read_op->data.dtr) { + f_pdata->use_dqs =3D true; + cqspi_phy_pre_config(cqspi, f_pdata, false); + ret =3D cqspi_phy_tuning_ddr(f_pdata, mem); + } else { + f_pdata->use_dqs =3D false; + cqspi_phy_pre_config(cqspi, f_pdata, true); + ret =3D cqspi_phy_tuning_sdr(f_pdata, mem); + } + + if (ret) + dev_warn(dev, "tuning failed: %d\n", ret); + + cqspi_phy_post_config(cqspi, f_pdata->read_delay); + +out: + /* + * Always restore the conservative base speed cap. On success, write + * back the validated maximum speed into the caller's op templates so + * that those specific ops bypass the cap in subsequent exec_op calls. + */ + mem->spi->base_speed_hz =3D base_speed; + if (!ret) { + read_op->max_freq =3D mem->spi->max_speed_hz; + if (write_op) + write_op->max_freq =3D mem->spi->max_speed_hz; + } + + return ret; +} + +static int cqspi_mem_op_execute_tuning(struct spi_mem *mem, + struct spi_mem_op *read_op, + struct spi_mem_op *write_op) +{ + struct cqspi_st *cqspi =3D + spi_controller_get_devdata(mem->spi->controller); + + if (!cqspi->ddata->execute_tuning) + return -EOPNOTSUPP; + + return cqspi->ddata->execute_tuning(mem, read_op, write_op); +} + static int cqspi_of_get_flash_pdata(struct platform_device *pdev, struct cqspi_flash_pdata *f_pdata, struct device_node *np) { + int nfreq, ret; + if (of_property_read_u32(np, "cdns,read-delay", &f_pdata->read_delay)) { dev_err(&pdev->dev, "couldn't determine read-delay\n"); return -ENXIO; @@ -1584,7 +3343,26 @@ static int cqspi_of_get_flash_pdata(struct platform_= device *pdev, return -ENXIO; } =20 - if (of_property_read_u32(np, "spi-max-frequency", &f_pdata->clk_rate)) { + /* + * spi-max-frequency accepts one or two values: + * - single rate; no tiered speed support + * - conservative default and higher maximum + * + * With two values the SPI core sets spi->base_speed_hz =3D base-freq and + * spi->max_speed_hz =3D max-freq. Store the second value here as the + * controller's higher rate target for calibration. + */ + nfreq =3D of_property_count_u32_elems(np, "spi-max-frequency"); + if (nfreq =3D=3D 2) { + ret =3D of_property_read_u32_index(np, "spi-max-frequency", 1, + &f_pdata->max_clk_rate); + if (ret) { + dev_err(&pdev->dev, "couldn't read spi-max-frequency[1]\n"); + return ret; + } + } else if (nfreq =3D=3D 1) { + f_pdata->max_clk_rate =3D 0; + } else { dev_err(&pdev->dev, "couldn't determine spi-max-frequency\n"); return -ENXIO; } @@ -1736,6 +3514,7 @@ static const struct spi_controller_mem_ops cqspi_mem_= ops =3D { .exec_op =3D cqspi_exec_mem_op, .get_name =3D cqspi_get_name, .supports_op =3D cqspi_supports_mem_op, + .execute_tuning =3D cqspi_mem_op_execute_tuning, }; =20 static const struct spi_controller_mem_caps cqspi_mem_caps =3D { @@ -2104,6 +3883,7 @@ static const struct cqspi_driver_platdata k2g_qspi = =3D { static const struct cqspi_driver_platdata am654_ospi =3D { .hwcaps_mask =3D CQSPI_SUPPORTS_OCTAL | CQSPI_SUPPORTS_QUAD, .quirks =3D CQSPI_NEEDS_WR_DELAY, + .execute_tuning =3D cqspi_am654_ospi_execute_tuning, }; =20 static const struct cqspi_driver_platdata intel_lgm_qspi =3D { --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from PH0PR06CU001.outbound.protection.outlook.com (mail-westus3azon11011003.outbound.protection.outlook.com [40.107.208.3]) (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 E039F44B692; Wed, 27 May 2026 17:56:29 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=40.107.208.3 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904591; cv=fail; b=Pz2+nSOiirypGXsSOyciE0/prDjEe0GcyWwaJg285ANKiv3oJYr6OcnQXbW4HQKMpDMxqnwFu5ifmPOIU0BzJ4yNjDV6KLUw5Ay2/qAQUWAm5ZnMdcx0uaFVllnyITxzCwk+sxC9dgluoa0ooORl9hYLHqbZvQv6LiprY1eFW7k= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904591; c=relaxed/simple; bh=+vUqGc88kG6akV0IeC51aCoJY9i7tRD2qEPSqSOovxI=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=k6fcQfcMExhaYyvMf1UehBNYvJyMfV0+L1CdIlEXyrLq/e4BImxKINM77/flxpIybf1J2oExVvPrVyTAOlxpnSL52cUVzzH4mF57hLso7SRrCNNnLnZdqryVYMV5+C4/a2832YOpgYKQIc5hgAjrxts9NWlvuub+4MAwoke+aKg= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=nBc33p95; arc=fail smtp.client-ip=40.107.208.3 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="nBc33p95" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=ZXIXt2BGRCuwp75xT5f8UkSz3rphUSyoiVqhrKs/yQwzL39j5uTovC1qVMklE1AT+PZN4FaZx4K40gkz7AxNSSqFUyFtd2TbiAkY7jcSoJXUaBgGy3LdFPKTG1tzCkXiqHqcNU3DPRGP0O+aU9uX0H0b2jvSuqkmSyqRrLsHhP1uWlZhhjTd8sabGlsHT5lbQPq4xcd6paAJtiobb5XmzoStZBrokWTvxoTtCpiX/cEJM455jcq9Jv+mnXT7F9a2xqWaWS/ZSr98R2Opb3zTfgplabslVSsTrS+fiF8zt21ElFabm3+hB5bYrGeYsFULhe4xvyrXy8Dy6X3s7l6ohQ== 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=3X1IUId+Hzuz475qNDT2KlwVBrZDXf19P3NMP/gh8h8=; b=da26kyDSvnoNNHBMUGchoUyw98tzWT+4pduFxrFuut5dppHpOv5JVWcITvEjRVObOZ0d0Uy0x+jNZrdN+9gu9fXjgoOZkGw1SCX6yBXqvkBytawk+Jp4zwnZvL9VzlvSF019EDBzQs0ZMdPBK8YYdvaVD7UKiNGoaeRGkPM9gyyYqWIS1iVLRRbFr1XA8AY92dV5XS0NHKrd3mqC5IYaS3/BLESR/qmdHXg2lMoVJFxO/0l5G0WKU1yD4TsxtVmw5zTG+fFsosclmLR0ZxcPQxZ5ZHBIODPHufISxY1PHx/1lx25scA2DF3tvZK6e3j3nBwIeW9HmokB+TVskO+klw== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=3X1IUId+Hzuz475qNDT2KlwVBrZDXf19P3NMP/gh8h8=; b=nBc33p95w7TZ4ERUH/Juu6F2mHi6Dmp9TE9ZyddSyL2Iaa1EQxiij4TTkfiq3QBpOJEAZy/K0XuzfvTJa+fQZdCvqZaRYsttTjFrTYuAbvJnshBresIfRgGMmB00Pl0/IbAOorWW4bAd8ibwAHBgdSbudDemUl/+KBF6JHJf9Qk= Received: from MW4PR03CA0206.namprd03.prod.outlook.com (2603:10b6:303:b8::31) by MW4PR10MB6371.namprd10.prod.outlook.com (2603:10b6:303:1ea::17) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.12; Wed, 27 May 2026 17:56:27 +0000 Received: from CO1PEPF00012E61.namprd05.prod.outlook.com (2603:10b6:303:b8:cafe::24) by MW4PR03CA0206.outlook.office365.com (2603:10b6:303:b8::31) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:56:27 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E61.mail.protection.outlook.com (10.167.249.70) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:26 +0000 Received: from DFLE202.ent.ti.com (10.64.6.60) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:25 -0500 Received: from DFLE214.ent.ti.com (10.64.6.72) by DFLE202.ent.ti.com (10.64.6.60) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:25 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE214.ent.ti.com (10.64.6.72) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:25 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpl4052476; Wed, 27 May 2026 12:56:20 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 09/13] spi: cadence-quadspi: reject 2-byte-address DDR ops on PHY-tunable hardware Date: Wed, 27 May 2026 23:25:23 +0530 Message-ID: <20260527175527.2247679-10-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E61:EE_|MW4PR10MB6371:EE_ X-MS-Office365-Filtering-Correlation-Id: bd878c98-bc76-4c3a-7a54-08debc1945d3 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|376014|7416014|82310400026|36860700016|1800799024|921020|22082099003|18002099003|6133799003|56012099006; X-Microsoft-Antispam-Message-Info: G3ZBiQ92rAYHYfVE8574+IEUodg7zklgpY9xaaD+3zhMGURnjPCfSvrhx/BYpfFSEXukt/okoIXopGL9YaICSpd+L/i6hYtSx3i+ZjWXCVB8TmQZLHDdtFkfROJKKcATsZXPlzlAulDDUg/LvCJbnbddUl07WUylHozhl8UNGiymOI73airEn/VGQ7QY91sWT8ypITLZQuW8Uk/Lc5OfiECNgK4BA9/9imi5FycqvEtTHWrBYzhMZXJIRGN8vv9YVhPK+aPPORHp8adynraPaPbChlx7BYIPAw7fVGlCw7SIYKCayRDTYJjQje8xjoalDT/tqPIOZ37Bl/hH4QQYlzvDJxjFszjiL4iz+fC4tUB3OP5j4TWGO+zsjk/bX3LXXhwdPgIHDlfKmkXlMBtSFA43XFP6X49hJZumNqVJ0ZhZBZs+lvGSqWdCs/xXq1PrrQ7NBkZm0bX4Mkh5PUOeJp5IcFWwA0xP1QB3SPljDBF0dUz+r+kojY5OJInOtrmzJMt12TJ1AiqX70MSDlJMx7nVy9Y2k2wsr1K7vP/P8gQ26uVtbdOo4c/aHtD6JTc/bv4qA5ErmTgLZI4O5LR510QgvInAgYvGdt78bsUKvnNLjpBsKOncOQXrV5y/mVUcy8K58GyFs7nOfH0b/lAzLy8PzCYpWDA0W/7l8rIMe9jZZBEoEzYc14VbU3DAKyFjlNi9Ap/y3lup3DY3RNRjgkEoBa9T8IKEQaKW/U6I2fxYdVPsADA8MTje29UlUomdi/naIjR4rlFUPyWjvQshkvf9sNcuKzwNS5+5TWs5NCI= X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(376014)(7416014)(82310400026)(36860700016)(1800799024)(921020)(22082099003)(18002099003)(6133799003)(56012099006);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: LT6cVgNyh2eewOxdKtEKmvwp5rSpUfURG80/CKW+cRns/I71Sv1ifRH1tH4j9Y2Fkl9uSx3a9/MDeY81lsbTF109ogXw6fYHmDzP7NNgeHEMGqwcgr9DxpefIJHVp1JoK2UUqysZCuWe0UM/ZkBx6Co/PfvUBh566MUDhpf19ozbJS1nBbGuLrycr/Zrq0L+uLHg1cTUBratlwQElW6sXV3ehKA46YGsWHfAhBcmGF/Vxh9O6m0KT9WkEN6l5egR6CpE/jvRG4awgBEDVRxlnAwqq1loZcheo9udTS8ll+zQJusdarp/BUFR4WPKLzsY6IWgGLYI7X7gbQmToLpwu1OFJbc11XiykEiQ/207iwVKpipKc28sw2ZUOn7EsIs573NXTo6OkUf5zKDhMsG9swoy2B7SpKwEGB9DElv0u6tCLnjuVqrKG/CAATWEqUU3 X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:26.3640 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: bd878c98-bc76-4c3a-7a54-08debc1945d3 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E61.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: MW4PR10MB6371 Content-Type: text/plain; charset="utf-8" Erratum i2383 affects the AM654 OSPI controller: in PHY DDR mode, operations with a 2-byte address cause an internal state machine to mis-compare the transmitted address byte count against 1 instead of 2, locking up the address phase. [0] Add a CQSPI_NO_2BYTE_ADDR_PHY_DDR quirk flag and set it on the am654_ospi platform data. In cqspi_supports_mem_op(), when a controller carries this quirk and has PHY tuning support, reject DDR operations that use 2-byte addressing. [0] https://www.ti.com/lit/er/sprz544c/sprz544c.pdf Signed-off-by: Santhosh Kumar K --- drivers/spi/spi-cadence-quadspi.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-qu= adspi.c index 508bc5bc4ab5..72208d376305 100644 --- a/drivers/spi/spi-cadence-quadspi.c +++ b/drivers/spi/spi-cadence-quadspi.c @@ -49,6 +49,7 @@ static_assert(CQSPI_MAX_CHIPSELECT <=3D SPI_DEVICE_CS_CNT= _MAX); #define CQSPI_DISABLE_RUNTIME_PM BIT(10) #define CQSPI_NO_INDIRECT_MODE BIT(11) #define CQSPI_HAS_WR_PROTECT BIT(12) +#define CQSPI_NO_2BYTE_ADDR_PHY_DDR BIT(13) =20 /* Capabilities */ #define CQSPI_SUPPORTS_OCTAL BIT(0) @@ -1627,6 +1628,18 @@ static bool cqspi_supports_mem_op(struct spi_mem *me= m, if (op->data.nbytes && op->data.buswidth !=3D 8) return false; =20 + /* + * Erratum i2383: In PHY DDR mode, 2-byte addressing causes an + * internal state machine to mis-compare the transmitted + * address byte count against 1 instead of 2, locking up the + * address phase. Reject such ops on controllers that need it. + */ + if (cqspi->ddata && + (cqspi->ddata->quirks & CQSPI_NO_2BYTE_ADDR_PHY_DDR)) { + if (op->addr.nbytes =3D=3D 2 && cqspi->ddata->execute_tuning) + return false; + } + if (cqspi->is_rzn1) return false; } else if (!all_false) { @@ -3882,7 +3895,7 @@ static const struct cqspi_driver_platdata k2g_qspi = =3D { =20 static const struct cqspi_driver_platdata am654_ospi =3D { .hwcaps_mask =3D CQSPI_SUPPORTS_OCTAL | CQSPI_SUPPORTS_QUAD, - .quirks =3D CQSPI_NEEDS_WR_DELAY, + .quirks =3D CQSPI_NEEDS_WR_DELAY | CQSPI_NO_2BYTE_ADDR_PHY_DDR, .execute_tuning =3D cqspi_am654_ospi_execute_tuning, }; =20 --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from DM1PR04CU001.outbound.protection.outlook.com (mail-centralusazon11010055.outbound.protection.outlook.com [52.101.61.55]) (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 627C044DB73; Wed, 27 May 2026 17:56:46 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.61.55 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904608; cv=fail; b=fENjIV5YT5zxX2hvEdU0ad2uYBhU7pPW8q/D+GF6OpfsYblm551S1G2HGN6A4ufuimzPa99BOL6HNnKYaBj7oeDZqhV+N6qGy2TDSH+chCL3YEuDMnxKJ63yTG67ofW1/NCa6ZH6LbiMeX6mKAhllR9bgT4sltzV26UPZabISBU= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904608; c=relaxed/simple; bh=x5026VJYgpv32C/t5gUEsKQrghWdVeWp7249LN35+S4=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=OkCuhMjnkq6FaQ3di6tME4xbST1YxTAzzXxaX+m8BcKdmdcsl2N4QEU5xrxkVimo34oODYj+orHRzIpcpxt84PbewI4ZpqjZAcPLn+WBFd2Q5zZzUbtSurP/4EQE5fVhPg52Av9pN5BAxx2iNzRQ49B6KD+7ujGPqg1tWfparQQ= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=YHMSzrvj; arc=fail smtp.client-ip=52.101.61.55 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="YHMSzrvj" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=ZVbB4bejmItFDLWWy07WyBzRu3E+LdO0AqnhNBgF0rQ0XoDrZEX2oFd1Ctwn/GM10bjomaj2SiOJChyRV05UKHxvRBWhc4JhRBZd1KDtzJojbfPLwnlfy5dWKzH/6n/n9uWe9QjqvEnHpSdhEofzFLsqGrCSGqtBnHIrB3xGNAZctSMaT985774Dd0GgTVFzFEKcV+odhg6sa1Fn0qS3bEOJ9RqvLBUnQy5mGDAC9KL9Atw0Gt69fNOJdHgmxwANL3QVV0pAFZzG3CIGwvyjelu55SMMSIsNu3p85vjcbvTiNFZufRlznUdrRLfTuJ8R2BchzL/UOiXQ603Z5V6bPQ== 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=nrgkYh+OQSJzz9OR8rqEleiqnFNmI2RXfBwBj88HpJw=; b=HDjJyfxc5pN2bnFsgpLaZaHDzawWa9cVDI1UnOEtHTwwNtyqmI+1WEPoQtQSWKeNLqWnWYqJ1G8ca86KIaa3McR9IFHYD+f1Jh5ziG24ZefQk29pdnfkPWJHBM6mgNUMyiutuW1eY6azBw7BMGeYbHHgwziEkGmSRA4h5i0R1QVZ4vyfBWCErWJy0lBtHxGVckb27/LCUmFY8aUT3xfMH86qTBtTA8y2F7oVooQ0rG+kwTrQ4Z0uvNHwGx/VN57rRgYkTF0J2TVlrq65jCBz2qHOfRxRieAHxdnE70fBHwKH7fevmPJRMd0HB9l8YJqknpXC5hUCReMSI+zk4F6VSA== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=nrgkYh+OQSJzz9OR8rqEleiqnFNmI2RXfBwBj88HpJw=; b=YHMSzrvjvLbHcwNa3puv61i/4CVJPTm/zQl19LYiG6RNjSp1TrCUqZLDU2Wq272Mjp9E/pwsnEZwZyaNpbAazsP60q9tYx0+v6H3XC6a7gcMQDjuN7jyDbJUnnmYQCnpOpdXm6Og7stk4D8+tmfYw6iF5vmpa4LIYPSWWEBWl5I= Received: from MW4PR03CA0207.namprd03.prod.outlook.com (2603:10b6:303:b8::32) by CH3PR10MB7460.namprd10.prod.outlook.com (2603:10b6:610:15e::20) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.12; Wed, 27 May 2026 17:56:42 +0000 Received: from CO1PEPF00012E61.namprd05.prod.outlook.com (2603:10b6:303:b8:cafe::7f) by MW4PR03CA0207.outlook.office365.com (2603:10b6:303:b8::32) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:56:41 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E61.mail.protection.outlook.com (10.167.249.70) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:40 +0000 Received: from DFLE211.ent.ti.com (10.64.6.69) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:30 -0500 Received: from DFLE204.ent.ti.com (10.64.6.62) by DFLE211.ent.ti.com (10.64.6.69) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:30 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE204.ent.ti.com (10.64.6.62) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:30 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpm4052476; Wed, 27 May 2026 12:56:25 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 10/13] spi: cadence-quadspi: enable PHY for direct reads and indirect writes Date: Wed, 27 May 2026 23:25:24 +0530 Message-ID: <20260527175527.2247679-11-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E61:EE_|CH3PR10MB7460:EE_ X-MS-Office365-Filtering-Correlation-Id: bf001038-49b8-48ec-b137-08debc194e58 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|376014|1800799024|7416014|36860700016|82310400026|22082099003|18002099003|921020|56012099006|6133799003; X-Microsoft-Antispam-Message-Info: y0QpqGk/r/aA51GcrZptqEx60XI2jHEGV+nuKZt9OhGcgUYXjoc34pyzmo0Gqb5UGRwDyIESCnHpT747AhLxFAF0UqQFri+VANBp+Oue8yGz1VOZEbkqL8WwaCzGX6cGWc+Uroq27HvtKlSfdK9eTF7HH4wHI29eEvhuFRhUE2f3gKYcU34cVOyCAcE9pul22HlLxZq9YXPjddkUCDFoAdn8OQqBpbn4rkShVf4BVw2BAFE1mdVsqSIczs/+14HL3YI6WJWKvqu4BOSz8DB9ltqt9dHl0kPypKP7f242+nAZ4cO++VfOhNUA5AejiyDf/qIC9G4w9WWOC9lj9WhE+rJjP6NRYYmQcrlZ/jzyn7Mio+WV3Z4pn1wbVXC39hVGQjymB26bMy3M/OY/1JryvMrkocD5z1M8nj1FYp8jCP00iMc2oX8Gt8jdEXT/inFub+/o+qcJlTpFAX9Tz6XOO4v71Tr49oyM4KmV0kFjcDcIK6Rkm75Vs0kZ3T0YFux213ultbv1CV/C2NOwBzkWp7J4c9xSheyaIWbnNUmQcD4BSbHROKnToeThAb3hGtk4H2t+xVsjzf5zgMjsDdIvdRJhlfd6m/PMorqoDd8rFjhuZgqqQsDTxgoK/HT9V5sYSQgyq1vJkrdAxksgqz3pDK6BhY/Nc7sYFFQCurq9rRaFV9pxyqKce21auXZT3MpnzJMY8h0wBD5XghRI43UHKp83rKHBdVr1JBuiL7TOKAZlRM+JA6osDfMArLBlMSSV0X/7T8MLj9FCUobAZqhftA== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(376014)(1800799024)(7416014)(36860700016)(82310400026)(22082099003)(18002099003)(921020)(56012099006)(6133799003);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: he/kCc78j0DvR9lVpYWNZTXH1JYDLgl+n1Zgbq2oIlEYVNriDWiIfMJ823SMSx6U4yo67XIP1b5LNoI0PdnOsN6eYLclY3kQxqvw0uADTqfhFW6N5CzefsOAFjuK7Y034JfbgKdmZohkBLBAXllsTVH3zb5TlYuggNg7dI4pN/g/xHzxRQy053/1ZEJe24Yf3/twD7o6WhrYdZ/b2jaxCRu8EZnYpbv3wG0mFMpo9XVdvz5DFmI1lc80VLlbHtnroPI41rySS1D7P3e8/fuNvrD1FZcyPwF1xcTPaYWsZOvtGKWfohrcnV0Oy7SXeu4MA2M1WumxuUdqA2htD6XbuD8GZ3eImOFAzM0ayp+TBO6SnynsukRVyscbutZg2UETARDrEdBZfvFvImfbxpbI/bKX9UDOVgzMgJbP9iFOX96FIG5A83g8E4T1A4xf9Ug4 X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:40.6478 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: bf001038-49b8-48ec-b137-08debc194e58 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E61.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: CH3PR10MB7460 Content-Type: text/plain; charset="utf-8" After PHY tuning completes, data transfers still use the default read-capture path. The PHY pipeline must be activated around each eligible transfer to benefit from the calibrated delay settings. Add cqspi_phy_enable() to toggle PHY mode. Enabling sets the calibrated read-capture delay, asserts PHY_EN and PHY_PIPELINE, and decrements the dummy cycle count by one since the PHY pipeline absorbs that latency. Disabling reverses all three. Returns cqspi_wait_idle() so callers can abort if the controller stalls on enable; disable is best-effort. Split cqspi_direct_read_execute() so PHY-eligible reads run DMA over the 16-byte-aligned middle section with PHY active, while unaligned head and tail bytes are transferred without PHY. PHY is used when use_phy is set, the transfer exceeds 16 bytes, and the frequency matches the tuned rate. cqspi_memcpy_fromio() handles small and non-DMA-able transfers, with special handling for 8D-8D-8D to ensure 2-byte-aligned I/O accesses. For indirect writes, PHY is enabled for transfers of at least 1 KB where the setup overhead is amortized. Signed-off-by: Santhosh Kumar K --- drivers/spi/spi-cadence-quadspi.c | 181 ++++++++++++++++++++++++++++-- 1 file changed, 171 insertions(+), 10 deletions(-) diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-qu= adspi.c index 72208d376305..80e7c572ab80 100644 --- a/drivers/spi/spi-cadence-quadspi.c +++ b/drivers/spi/spi-cadence-quadspi.c @@ -564,6 +564,61 @@ static void cqspi_readdata_capture(struct cqspi_st *cq= spi, const bool bypass, writel(reg, reg_base + CQSPI_REG_READCAPTURE); } =20 +static int cqspi_phy_enable(struct cqspi_flash_pdata *f_pdata, bool enable) +{ + struct cqspi_st *cqspi =3D f_pdata->cqspi; + void __iomem *reg_base =3D cqspi->iobase; + u32 reg; + u8 dummy; + + if (enable) { + cqspi_readdata_capture(cqspi, true, f_pdata->use_dqs, + f_pdata->phy_setting.read_delay); + + reg =3D readl(reg_base + CQSPI_REG_CONFIG); + reg |=3D CQSPI_REG_CONFIG_PHY_EN | CQSPI_REG_CONFIG_PHY_PIPELINE; + writel(reg, reg_base + CQSPI_REG_CONFIG); + + /* + * The PHY data-capture pipeline absorbs one dummy cycle's + * worth of latency; reduce the count to avoid over-compensation. + */ + reg =3D readl(reg_base + CQSPI_REG_RD_INSTR); + dummy =3D FIELD_GET(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + reg); + dummy--; + reg &=3D ~(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB); + reg |=3D FIELD_PREP(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + dummy); + writel(reg, reg_base + CQSPI_REG_RD_INSTR); + } else { + cqspi_readdata_capture(cqspi, !cqspi->rclk_en, false, + f_pdata->read_delay); + + reg =3D readl(reg_base + CQSPI_REG_CONFIG); + reg &=3D ~(CQSPI_REG_CONFIG_PHY_EN | + CQSPI_REG_CONFIG_PHY_PIPELINE); + writel(reg, reg_base + CQSPI_REG_CONFIG); + + reg =3D readl(reg_base + CQSPI_REG_RD_INSTR); + dummy =3D FIELD_GET(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + reg); + dummy++; + reg &=3D ~(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB); + reg |=3D FIELD_PREP(CQSPI_REG_RD_INSTR_DUMMY_MASK + << CQSPI_REG_RD_INSTR_DUMMY_LSB, + dummy); + writel(reg, reg_base + CQSPI_REG_RD_INSTR); + } + + return cqspi_wait_idle(cqspi); +} + static int cqspi_exec_flash_cmd(struct cqspi_st *cqspi, unsigned int reg) { void __iomem *reg_base =3D cqspi->iobase; @@ -1191,6 +1246,7 @@ static int cqspi_indirect_write_execute(struct cqspi_= flash_pdata *f_pdata, void __iomem *reg_base =3D cqspi->iobase; unsigned int remaining =3D n_tx; unsigned int write_bytes; + bool use_phy_write; int ret; =20 if (!refcount_read(&cqspi->refcount)) @@ -1226,6 +1282,15 @@ static int cqspi_indirect_write_execute(struct cqspi= _flash_pdata *f_pdata, if (cqspi->apb_ahb_hazard) readl(reg_base + CQSPI_REG_INDIRECTWR); =20 + /* Use PHY only for large writes where setup overhead is amortized */ + use_phy_write =3D n_tx >=3D SZ_1K && f_pdata->use_phy; + + if (use_phy_write) { + ret =3D cqspi_phy_enable(f_pdata, true); + if (ret) + goto failwr; + } + while (remaining > 0) { size_t write_words, mod_bytes; =20 @@ -1266,6 +1331,9 @@ static int cqspi_indirect_write_execute(struct cqspi_= flash_pdata *f_pdata, goto failwr; } =20 + if (use_phy_write) + cqspi_phy_enable(f_pdata, false); + /* Disable interrupt. */ writel(0, reg_base + CQSPI_REG_IRQMASK); =20 @@ -1277,6 +1345,9 @@ static int cqspi_indirect_write_execute(struct cqspi_= flash_pdata *f_pdata, return 0; =20 failwr: + if (use_phy_write) + cqspi_phy_enable(f_pdata, false); + /* Disable interrupt. */ writel(0, reg_base + CQSPI_REG_IRQMASK); =20 @@ -1448,8 +1519,15 @@ static void cqspi_rx_dma_callback(void *param) complete(&cqspi->rx_dma_complete); } =20 -static int cqspi_direct_read_execute(struct cqspi_flash_pdata *f_pdata, - u_char *buf, loff_t from, size_t len) +static bool cqspi_use_phy(struct cqspi_flash_pdata *f_pdata, + const struct spi_mem_op *op) +{ + return f_pdata->use_phy && op->data.nbytes > 16 && + op->max_freq =3D=3D f_pdata->max_clk_rate; +} + +static int cqspi_direct_read_dma(struct cqspi_flash_pdata *f_pdata, u_char= *buf, + loff_t from, size_t len) { struct cqspi_st *cqspi =3D f_pdata->cqspi; struct device *dev =3D &cqspi->pdev->dev; @@ -1461,19 +1539,14 @@ static int cqspi_direct_read_execute(struct cqspi_f= lash_pdata *f_pdata, dma_addr_t dma_dst; struct device *ddev; =20 - if (!cqspi->rx_chan || !virt_addr_valid(buf)) { - memcpy_fromio(buf, cqspi->ahb_base + from, len); - return 0; - } - ddev =3D cqspi->rx_chan->device->dev; dma_dst =3D dma_map_single(ddev, buf, len, DMA_FROM_DEVICE); if (dma_mapping_error(ddev, dma_dst)) { dev_err(dev, "dma mapping failed\n"); return -ENOMEM; } - tx =3D dmaengine_prep_dma_memcpy(cqspi->rx_chan, dma_dst, dma_src, - len, flags); + tx =3D dmaengine_prep_dma_memcpy(cqspi->rx_chan, dma_dst, dma_src, len, + flags); if (!tx) { dev_err(dev, "device_prep_dma_memcpy error\n"); ret =3D -EIO; @@ -1507,6 +1580,94 @@ static int cqspi_direct_read_execute(struct cqspi_fl= ash_pdata *f_pdata, return ret; } =20 +static void cqspi_memcpy_fromio(const struct spi_mem_op *op, void *to, + const void __iomem *from, size_t count) +{ + if (op->data.buswidth =3D=3D 8 && op->data.dtr) { + unsigned long from_addr =3D (unsigned long)from; + + /* Handle unaligned start with 2-byte read */ + if (count && !IS_ALIGNED(from_addr, 4)) { + *(u16 *)to =3D __raw_readw(from); + from +=3D 2; + to +=3D 2; + count -=3D 2; + } + + /* Use 4-byte reads for aligned bulk (no readq for 32-bit) */ + if (count >=3D 4) { + size_t len =3D round_down(count, 4); + + memcpy_fromio(to, from, len); + from +=3D len; + to +=3D len; + count -=3D len; + } + + /* Handle remaining 2 bytes */ + if (count) + *(u16 *)to =3D __raw_readw(from); + + return; + } + + memcpy_fromio(to, from, count); +} + +static int cqspi_direct_read_execute(struct cqspi_flash_pdata *f_pdata, + const struct spi_mem_op *op) +{ + struct cqspi_st *cqspi =3D f_pdata->cqspi; + loff_t from =3D op->addr.val; + loff_t from_aligned, to_aligned; + size_t len =3D op->data.nbytes; + size_t len_aligned; + u_char *buf =3D op->data.buf.in; + int ret; + + if (!cqspi->rx_chan || !virt_addr_valid(buf) || len <=3D 16) { + cqspi_memcpy_fromio(op, buf, cqspi->ahb_base + from, len); + return 0; + } + + if (!cqspi_use_phy(f_pdata, op)) + return cqspi_direct_read_dma(f_pdata, buf, from, len); + + /* Split into unaligned head, aligned middle, unaligned tail */ + from_aligned =3D ALIGN(from, 16); + to_aligned =3D ALIGN_DOWN(from + len, 16); + len_aligned =3D to_aligned - from_aligned; + + if (from !=3D from_aligned) { + ret =3D cqspi_direct_read_dma(f_pdata, buf, from, + from_aligned - from); + if (ret) + return ret; + buf +=3D from_aligned - from; + } + + if (len_aligned) { + ret =3D cqspi_phy_enable(f_pdata, true); + if (ret) + return ret; + ret =3D cqspi_direct_read_dma(f_pdata, buf, from_aligned, + len_aligned); + cqspi_phy_enable(f_pdata, false); + if (ret) + return ret; + buf +=3D len_aligned; + } + + if (to_aligned !=3D (from + len)) { + ret =3D cqspi_direct_read_dma(f_pdata, buf, to_aligned, + (from + len) - to_aligned); + if (ret) + return ret; + } + + return 0; +} + static ssize_t cqspi_read(struct cqspi_flash_pdata *f_pdata, const struct spi_mem_op *op) { @@ -1524,7 +1685,7 @@ static ssize_t cqspi_read(struct cqspi_flash_pdata *f= _pdata, =20 if ((cqspi->use_direct_mode && ((from + len) <=3D cqspi->ahb_size)) || (cqspi->ddata && cqspi->ddata->quirks & CQSPI_NO_INDIRECT_MODE)) - return cqspi_direct_read_execute(f_pdata, buf, from, len); + return cqspi_direct_read_execute(f_pdata, op); =20 if (cqspi->use_dma_read && ddata && ddata->indirect_read_dma && virt_addr_valid(buf) && ((dma_align & CQSPI_DMA_UNALIGN) =3D=3D 0)) --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from BL0PR03CU003.outbound.protection.outlook.com (mail-eastusazon11012063.outbound.protection.outlook.com [52.101.53.63]) (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 2078F30F55F; Wed, 27 May 2026 17:56:42 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.53.63 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904604; cv=fail; b=YQtb5QeOfjcnO8lxecL/NPpQ33ecSCI9O7OTvGEmQoO2Qb6MrNgvON0KvXKm6TvKZs9+9WVY2D6nvXp/zCgkP3cUjUfhYdV2itqMEZFv6Ur/NunxE+5JaUimme6zfLTJQsjy469uQJV22zB/GuKB44pDbjXdK/K0qbtBknUBJLA= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904604; c=relaxed/simple; bh=9e802VeJMp3qtlWhTs1SZXBE0kobyq34dMyyPthayws=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=Kbe8QH+c5hJX3X8b11B4UM2Ak1jNgxc4i/Ao8p1Gbq9DxIPfKbKsjJAl/lCvqi3y/HfsAWV0tcPhpERZJUxab6cToKizSby/Mvi/wsDNYRmd2eL3edu8xmo318Fn0zv/SI1KJXH7Ddgq6aVTDmPzfobqcSB+TVZ9VDVUQyQjBD0= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=KOsTQP/g; arc=fail smtp.client-ip=52.101.53.63 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="KOsTQP/g" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=i9cypyHBDjuxR7u+Plpr3mHN9tIEeyrIkTt8004WQZHDphs+TITEMd7RA2POi7/kG6q+CHttSupDMD6F7U0bBdivirjZSx6aLO4UzsSsibTiHxsbdVYXCSNb3U8Ra18cJzw7U1qvdbSopPekbVNpeSDn2rHwKQzxVN2l+PzvoggC6MXFm0ppeDW5fzfs1aet+SZFRlNVjEh5kx1bSDSntpny03915ohNgMmpURHsxLO0/gRVh8tRda5sNfeEoDbDHfQcuN7lGaRdK9e17gJkb8Xbos36NobQ9vaNhk63h+Y7dxFV+brlaI/85ji6SxL5C9tF1cLywIlI3LyCjeWkzQ== 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=tSFK1LcSZX0OA7Az20GmaFFaMbMXhDuR3o6DZJCyo60=; b=xElSGBHL6yWulKpasj/jQ2VdZzNNLUjlXJW7wGugij5FZQD3NSWlRhgKJLv4MZiwl+mqvqf9IyyRJfDEdHmxaR0vf4HVy8xOdEYhx8Q/ftHDAVM7XmwaqqfXgVNoymVIPaSEaIdIjInmyv2dLiMhu4OtMk3JyDuU40FEmTr8scRo3NN7qow+mj9wS9z9F0T0XBgicYrNTl9kJwhnG5X5zl+nlKS7Ab3kFv7P1FNihC5s+kIcfaoogtLTmgkewhYKhKmZFdkGgDgaUfsUpg7THTloYFHg70w2CfsSqd4OMITgoDq0U0H+WZSTYLp8nVDEb7wcv3N+XnFqEJNaL5sUWw== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.23.194) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=tSFK1LcSZX0OA7Az20GmaFFaMbMXhDuR3o6DZJCyo60=; b=KOsTQP/grEIlfJ03eiLjijSTl1g9m2oIVUY9qo/ABrSimC0hZ2uuqSuRefBmgggD2QQ0sgiGK6v000zKuyo/mFlDobL7poFSJDjJsYJ9PmnvfPaHWbFW2mQWEOkXGH3AH1B/bWdGy0Ve2gz6jkTNnNZF1dhwdZMb9eImwLZ4cSo= Received: from CYZPR14CA0025.namprd14.prod.outlook.com (2603:10b6:930:a0::27) by PH0PR10MB5643.namprd10.prod.outlook.com (2603:10b6:510:fa::22) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.11; Wed, 27 May 2026 17:56:39 +0000 Received: from DM2PEPF00003FC6.namprd04.prod.outlook.com (2603:10b6:930:a0:cafe::3c) by CYZPR14CA0025.outlook.office365.com (2603:10b6:930:a0::27) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:56:39 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.23.194) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.23.194 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.23.194; helo=lewvzet200.ext.ti.com; pr=C Received: from lewvzet200.ext.ti.com (198.47.23.194) by DM2PEPF00003FC6.mail.protection.outlook.com (10.167.23.25) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:38 +0000 Received: from DLEE204.ent.ti.com (157.170.170.84) by lewvzet200.ext.ti.com (10.4.14.103) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:36 -0500 Received: from DLEE210.ent.ti.com (157.170.170.112) by DLEE204.ent.ti.com (157.170.170.84) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:35 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DLEE210.ent.ti.com (157.170.170.112) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:35 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpn4052476; Wed, 27 May 2026 12:56:31 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 11/13] mtd: spinand: run PHY tuning after init and update dirmap frequencies Date: Wed, 27 May 2026 23:25:25 +0530 Message-ID: <20260527175527.2247679-12-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: DM2PEPF00003FC6:EE_|PH0PR10MB5643:EE_ X-MS-Office365-Filtering-Correlation-Id: 488ca640-f2a9-4dbc-ab4e-08debc194d3e X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|82310400026|376014|7416014|36860700016|1800799024|921020|6133799003|22082099003|18002099003|56012099006; X-Microsoft-Antispam-Message-Info: KTuMe1wUMQNGGsrzfZCqyxqUTsUN52dF7cudpfgXcwd8nceyb0PDy9pV99xxT/82cLaZb8ICECF8eg7xC4xZKVFDlz3YgWtEGmwI9h2YSGOeIvuih1L9ZWVuUw7gYzBtIM+EOJ1TsTL+ndDBk+UkWtx4YSYsPAUjemY/IlNTuaIh0kH4Xf3UCxi2QJZJ2xMg2V9l1Ab68UWHR7AV+3YL0TZfq5PGgkjpiJLmNYM85IaqZCIaA/SE56DNcPDSc71DmuexiKfeJuYfmh7NZu7H15lRXxDWeZpSL1PkFO8C9/tiRcYfZeuBhmqMETtXgrxAh+OKffjSvPDmLeSXmb8LvZvfkJiQAn0bHo9S2hOHsX144FG2IE+t8jbgUlG9BtHWpDRB4vJNWBIn/0tpr6HFMxGk7pPE9GsoZyLfj5PfZRKn+nlqySVpfVoFtnR4e3ARz5QPRFRJCDFQkTzwYd18yE2zrq9fEjU6Jkb53otgC1PE9MZfCU/h+cTDWbffqu4j4PaHVGUXZJ23trjmlyYt8yHQ7KOYQbjb1EoKE3Py60LJpFQPIiaOUUpcBChWRO4LBxdnSWECWgKP1wqe6piZI6ZWFlu0YYqYmchEyZv186LQ2euhl+Hb4Yjt2q35snV/yTijQSy5Zw6zVS390GjhD0U77AJivH85fylPbsewQX2sCeYcu7Sz/xSj2dOzU/M4OSyOn+amDu8FH8fW6ErFBg5XrtmNMy0BuL0KYDXzb3m3KUZCOZtEkFJ5bmIpTr+HkrHlqy22ICVBZBCzGWXE9Q== X-Forefront-Antispam-Report: CIP:198.47.23.194;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:lewvzet200.ext.ti.com;PTR:InfoDomainNonexistent;CAT:NONE;SFS:(13230040)(82310400026)(376014)(7416014)(36860700016)(1800799024)(921020)(6133799003)(22082099003)(18002099003)(56012099006);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: x+LLh/BiuRHNaOaKpuIsG2Bq3b607cwyv45BU6PKoNGZABK31BbuL0ZW1IydH0KyoAWpopKRBHfzCoTgMNesomshOAj1swFgMJbRowKWHBmCnOMKy2xJBCazubG7gv6fkJ+YNEtJ/9XK/BbpFPwv+5HAVeTn1r8vaDuGeM3CmHFDuQOsJtOyQwNYzt47FohA5+DUsamqXQSbBVFaWsH8NJ46d+x+JP+m0u3BvebQiQ75ntNcm8LuJ54EwBO5NkhNnX0vJeubMh7mm94WARR76r+BiEGwJpyGJ8BKJ9zWIt20hVAgX1RRTqi+s30EOkQJ4gO4jX0k7H5vZagIHsgD9IfistbROezoCuzqclWdMBNwNR/cLy/QNlTlI8qDqH1z2kClzmK/evY3PMqIZvFf87fUO1jaf9wip1F+wtvuDNKbBO4Ypzw/nRSnv2WezRtn X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:38.8398 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 488ca640-f2a9-4dbc-ab4e-08debc194d3e X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.23.194];Helo=[lewvzet200.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: DM2PEPF00003FC6.namprd04.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: PH0PR10MB5643 Content-Type: text/plain; charset="utf-8" Run spi_mem_execute_tuning() in spinand_probe() after spinand_init() completes. The read and write op templates are copied into persistent fields in spinand_device so the controller can write the validated frequency directly back into them. On success, propagate that frequency to every dirmap's primary and secondary op templates. Updating the secondary template ensures continuous-read dirmaps also benefit from the validated speed, not just the primary read path. Signed-off-by: Santhosh Kumar K --- drivers/mtd/nand/spi/core.c | 35 +++++++++++++++++++++++++++++++++++ include/linux/mtd/spinand.h | 4 ++++ 2 files changed, 39 insertions(+) diff --git a/drivers/mtd/nand/spi/core.c b/drivers/mtd/nand/spi/core.c index f1084d5e04b9..9b54e4607cfe 100644 --- a/drivers/mtd/nand/spi/core.c +++ b/drivers/mtd/nand/spi/core.c @@ -2030,6 +2030,41 @@ static int spinand_probe(struct spi_mem *mem) if (ret) return ret; =20 + /* + * Copy the read and write op templates into persistent fields so + * execute_tuning can write the validated frequency back into them. + * Tuning failure is non-fatal; the device operates at base speed. + */ + spinand->max_read_op =3D *spinand->op_templates->read_cache; + spinand->max_write_op =3D *spinand->op_templates->write_cache; + + ret =3D spi_mem_execute_tuning(mem, &spinand->max_read_op, + &spinand->max_write_op); + if (ret && ret !=3D -EOPNOTSUPP) + dev_warn(&mem->spi->dev, "Failed to execute PHY tuning: %d\n", + ret); + + /* + * Dirmaps were set up in spinand_init() before tuning ran; update + * their op templates to use the validated frequency. + */ + if (!ret) { + struct nand_device *nand =3D spinand_to_nand(spinand); + int i; + + for (i =3D 0; i < nand->memorg.planes_per_lun; i++) { + if (spinand->dirmaps[i].rdesc) { + spinand->dirmaps[i].rdesc->info.primary_op_tmpl.max_freq =3D + spinand->max_read_op.max_freq; + spinand->dirmaps[i].rdesc->info.secondary_op_tmpl.max_freq =3D + spinand->max_read_op.max_freq; + } + if (spinand->dirmaps[i].wdesc) + spinand->dirmaps[i].wdesc->info.primary_op_tmpl.max_freq =3D + spinand->max_write_op.max_freq; + } + } + ret =3D mtd_device_register(mtd, NULL, 0); if (ret) goto err_spinand_cleanup; diff --git a/include/linux/mtd/spinand.h b/include/linux/mtd/spinand.h index 44f4347104d6..e5af90281762 100644 --- a/include/linux/mtd/spinand.h +++ b/include/linux/mtd/spinand.h @@ -786,6 +786,10 @@ struct spinand_device { =20 struct spinand_dirmap *dirmaps; =20 + /* Persistent op templates updated by execute_tuning with validated speed= . */ + struct spi_mem_op max_read_op; + struct spi_mem_op max_write_op; + int (*select_target)(struct spinand_device *spinand, unsigned int target); unsigned int cur_target; --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from MW6PR02CU001.outbound.protection.outlook.com (mail-westus2azon11012000.outbound.protection.outlook.com [52.101.48.0]) (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 1993D3812EF; Wed, 27 May 2026 17:56:48 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.48.0 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904610; cv=fail; b=jZ/Zg/qo1RC6LhY8+ULSbbBOZjMyq0Yes/NOVHwCANi6+xca/6gdaXfLzSU15OoHHx6WvOjMAgwQpF4RR/bE3RMSG3sVCwoJ+gW25JihYZcxomvkXL0YvYXcU9z3DEiUbqXmBr9r2+WwDN35N1BStRYLXzYBLPA+Jdu7cgHV9D0= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904610; c=relaxed/simple; bh=5/V5ukoiwSHKB8So05WQQ46hsjXpQ7uElOLSGrLE9RM=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=oAQ7Sv0B6X7u7CcVswLuw9nayjWq6NIj6Pzf41Nl44AjTen8GBvnu/HVpgRNzmGCr6pFjWIF8YCtA+g/vvHr37rgvj0NNSuSFqkinnoal7OzCsFbhBQXlCSi8gPiZwoNCtvmdyCmnPHFd3DFdSrquKNuCCycsjxywdXUA4E/u/g= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=bMjDHtA+; arc=fail smtp.client-ip=52.101.48.0 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="bMjDHtA+" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=jd7Wq8aOUhazoeUJUT8BnUxgBwhu1M8QcQoC/yAku6Syh5LMq0cBJyRn6kFqwIPu9TTHB5Ejga46lJTa9IWSVayBvmeY0oaJ5r/g1TJjMNMf7BkYGjFoLYSsqqh5UAdTVmwDb3tcW8NFSOYgCcdO2y3AoOAogmd0FPi3fKUz0sbZdU5J8KjW7h/0dp5wL4zyQapVv8Vr61oJH10/teFI9QEYsDmm+BVQnLp41DADz0W67kNtk04HMVITHRORbw5WOMSABovTsU/JYRqgsf07cHzED0xv3W+WZps56IvF2KLfbuc09YL6fDF2cMGXbYxZknrdBIEAyaF38+CskrDewQ== 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=ppe0qTwspSHUu7S5lBvqAOYj2cYyzZrEkwbB0LCOMqw=; b=F8kHADHxKACezTePBZ3V/Lqd19Ci8N1vaxIOg8gqZtRKxAqeRlE/lNcbj5hrVICzYK9YtOKPTRpOZtIhQ4Z1vEEo7ED/kbu2f5ODBy5swxdMjzmk7uwKlKHdcLHLg4ylvCPxbKnej/4BEOQ851Rm/8V4yoe8NLt7PhciwelEN8dEchdQ7i0lSHNWzncFClI6XHIrQUQsPHfwgKkxU0+r2I+amgsrS6tPVD7qecPtfrSsl63KlB+xsXTyDAkEpZCkhy3Hi/GvmhQ1m5s4e8Y/ZW/gdEPFgFpzVKIWFF6jJmYhNEHiSKCHDwTGDkHhSpDP9hckqvCbWU8h9/Z5zhugfg== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.23.194) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=ppe0qTwspSHUu7S5lBvqAOYj2cYyzZrEkwbB0LCOMqw=; b=bMjDHtA+gjKXW70zfac1KlpeIf3GdX+pwcuKPJzcR+S+qcUwNpPAqaBWDO6ZSFj/Czw7UZgluGDA+FdEBhGdZoDPY/SIFaJezvNoTz7Y5JcJoYyI9HHOoE9s0/8X/rOvZWUBPkIBqHckYmByPZoaE/ic6iRazzHPC3JNNFAtPR8= Received: from CYZPR14CA0044.namprd14.prod.outlook.com (2603:10b6:930:a0::28) by PH0PR10MB5731.namprd10.prod.outlook.com (2603:10b6:510:149::16) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.12; Wed, 27 May 2026 17:56:44 +0000 Received: from DM2PEPF00003FC6.namprd04.prod.outlook.com (2603:10b6:930:a0:cafe::20) by CYZPR14CA0044.outlook.office365.com (2603:10b6:930:a0::28) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:56:43 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.23.194) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.23.194 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.23.194; helo=lewvzet200.ext.ti.com; pr=C Received: from lewvzet200.ext.ti.com (198.47.23.194) by DM2PEPF00003FC6.mail.protection.outlook.com (10.167.23.25) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:43 +0000 Received: from DLEE213.ent.ti.com (157.170.170.116) by lewvzet200.ext.ti.com (10.4.14.103) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:41 -0500 Received: from DLEE212.ent.ti.com (157.170.170.114) by DLEE213.ent.ti.com (157.170.170.116) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:40 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DLEE212.ent.ti.com (157.170.170.114) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:40 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpo4052476; Wed, 27 May 2026 12:56:36 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 12/13] mtd: spi-nor: extract read op template construction into helper Date: Wed, 27 May 2026 23:25:26 +0530 Message-ID: <20260527175527.2247679-13-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: DM2PEPF00003FC6:EE_|PH0PR10MB5731:EE_ X-MS-Office365-Filtering-Correlation-Id: a8973108-1f87-4f53-500d-08debc195030 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|1800799024|36860700016|376014|82310400026|7416014|18002099003|22082099003|921020|3023799007|56012099006; X-Microsoft-Antispam-Message-Info: 5sXJy9vLXdzNrdpDu9bCLC5izva2pr3im0Vvm5JsS2FBrLY8wZYAo6UfloMzBaI36gva4wiUkkbKQlpQKjQOnNcpWmzqXOIZeyzyX4/46rA3DnDjBsxRbS/FAfva2JWwMP7C50cOvCRdfaNgst7auMwP9SKjeo23LMrHottMmU0QKRlIUI4SFLq1rz2wGqPvanNN6wFcYIBaHxFE/vFbkleKHIGFIOGyPdkvNt6z/uMR7MvATVGIa5nvYSyKh72LPoWO2ioUZu8Tj2vBmhp+7INe4Ta5+mh+/qsWgBVhw5tt7Yxq3mOkiJS8b8JRF1pfcKADy80PhyshLk9Biwd1mj0m2LIeKK8IjVlQD1hIqd9+PQWPEV/bju2RrchdQDx+7MhjTE4CuQtzYZRnvml8tB7UJMX2m/naKfwaXh6wGyUSrrr6y3WVGITwEVMsd66NX76LF0uVYc9hddrHiYK335smAPLJ6JgsTYwmohxegcMUFIRBMgBpjUm+6UqtCOKhrAM/XjSFA2DKGB5PGY6d4doam40s/Tm6oqhV0u9+btZh5iZQzd8TZuojyS38k+SXrDlZ3uRPi/m2TOE68sFI1VDqmo4GsqpTeAILeZwt2F2xfucgIy2ArAW5nh/mZ+CseEacDiIwBZZ7A+TGT6rd7mNHebcXPqAfED6t/ZjuZ8s/+CM6TjnFE8WptDal9lt8F8RBAMtx/dKUyA4KtGb1iUY8t/n897/R6ofYJii4/e1Y/wI2bV6GujBzdhWD75V2kXFnc7Ppv6HMBjUnS4DRyw== X-Forefront-Antispam-Report: CIP:198.47.23.194;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:lewvzet200.ext.ti.com;PTR:InfoDomainNonexistent;CAT:NONE;SFS:(13230040)(1800799024)(36860700016)(376014)(82310400026)(7416014)(18002099003)(22082099003)(921020)(3023799007)(56012099006);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: W0gwlrsKAckqg5XVtRzFnSaW7p5R5zPqZo9+En1TyB6Ru/1hE76oYvKtlLqh5txPVpcZPuHEvw3sbqdrWe6JWsGy16+NHicN4GJrhY+L7OSoPoOCGJNHBHx8oJdCiwCyWg284dexsOcGnH7C/59qka9JvNBIAo2WMMUUcSaUUwUTUkAUB1gMA7oZpVzOAQD54iWtU3LFpcQ2oyAgtTZhNNQE5ihsM8f5+gJhFDjqfXUcb3NCLwRJ6E0G5J+4fu1ZrJEX9HeCmvB5CW6oG6yR0NTEh5BCb8jN6Du+hMlKqKsBNSDWEU4pMx/0+APsextH8/8IFg7gzjQf6heTMqch8f/ePEYtmzLkg3gK/6m+lvGcSr8vNPUnMfucQEeTa+jorPm9zw1Danec1gJArHkuyuw2BflsXM0+OqOhVmk/nDxjrr7JLAhMkADW4HYTwMde X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:43.7686 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: a8973108-1f87-4f53-500d-08debc195030 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.23.194];Helo=[lewvzet200.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: DM2PEPF00003FC6.namprd04.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: PH0PR10MB5731 From: Pratyush Yadav spi_nor_spimem_read_data() and spi_nor_create_read_dirmap() both open-coded the same sequence: build the read spi_mem_op, call spi_nor_spimem_setup_op(), convert dummy cycles to bytes, and=E2=80=94in the dirmap case=E2=80=94explicitly patch data.buswidth because setup_op skips it when data.nbytes is zero. Introduce spi_nor_spimem_get_read_op() to centralise this logic. Initialising the op with data.nbytes set to a non-zero value ensures spi_nor_spimem_setup_op() populates data.buswidth, removing the need for the manual override in the dirmap path. The dirmap template is initialised directly from the helper; direct-read callers overwrite addr.val, data.nbytes, and data.buf.in before submitting. Signed-off-by: Pratyush Yadav Signed-off-by: Santhosh Kumar K --- drivers/mtd/spi-nor/core.c | 66 +++++++++++++++++++++----------------- 1 file changed, 36 insertions(+), 30 deletions(-) diff --git a/drivers/mtd/spi-nor/core.c b/drivers/mtd/spi-nor/core.c index a7bc458edc5c..2c9859fb0794 100644 --- a/drivers/mtd/spi-nor/core.c +++ b/drivers/mtd/spi-nor/core.c @@ -188,6 +188,37 @@ static int spi_nor_controller_ops_erase(struct spi_nor= *nor, loff_t offs) return nor->controller_ops->erase(nor, offs); } =20 +/** + * spi_nor_spimem_get_read_op() - build a configured read op template + * @nor: the spi-nor device + * + * Returns a spi_mem_op with the command, address format, dummy cycles, + * and data buswidth configured for @nor. For direct reads, the caller + * must fill in addr.val, data.nbytes, and data.buf.in before use. + */ +static struct spi_mem_op spi_nor_spimem_get_read_op(struct spi_nor *nor) +{ + /* + * data.nbytes must be non-zero so spi_nor_spimem_setup_op() + * configures the data buswidth; callers replace it with the + * actual transfer length. + */ + struct spi_mem_op op =3D + SPI_MEM_OP(SPI_MEM_OP_CMD(nor->read_opcode, 0), + SPI_MEM_OP_ADDR(nor->addr_nbytes, 0, 0), + SPI_MEM_OP_DUMMY(nor->read_dummy, 0), + SPI_MEM_OP_DATA_IN(2, NULL, 0)); + + spi_nor_spimem_setup_op(nor, &op, nor->read_proto); + + /* convert the dummy cycles to the number of bytes */ + op.dummy.nbytes =3D (nor->read_dummy * op.dummy.buswidth) / 8; + if (spi_nor_protocol_is_dtr(nor->read_proto)) + op.dummy.nbytes *=3D 2; + + return op; +} + /** * spi_nor_spimem_read_data() - read data from flash's memory region via * spi-mem @@ -201,21 +232,14 @@ static int spi_nor_controller_ops_erase(struct spi_no= r *nor, loff_t offs) static ssize_t spi_nor_spimem_read_data(struct spi_nor *nor, loff_t from, size_t len, u8 *buf) { - struct spi_mem_op op =3D - SPI_MEM_OP(SPI_MEM_OP_CMD(nor->read_opcode, 0), - SPI_MEM_OP_ADDR(nor->addr_nbytes, from, 0), - SPI_MEM_OP_DUMMY(nor->read_dummy, 0), - SPI_MEM_OP_DATA_IN(len, buf, 0)); + struct spi_mem_op op =3D spi_nor_spimem_get_read_op(nor); bool usebouncebuf; ssize_t nbytes; int error; =20 - spi_nor_spimem_setup_op(nor, &op, nor->read_proto); - - /* convert the dummy cycles to the number of bytes */ - op.dummy.nbytes =3D (nor->read_dummy * op.dummy.buswidth) / 8; - if (spi_nor_protocol_is_dtr(nor->read_proto)) - op.dummy.nbytes *=3D 2; + op.addr.val =3D from; + op.data.nbytes =3D len; + op.data.buf.in =3D buf; =20 usebouncebuf =3D spi_nor_spimem_bounce(nor, &op); =20 @@ -3642,28 +3666,10 @@ static int spi_nor_create_read_dirmap(struct spi_no= r *nor) { struct spi_mem_dirmap_info info =3D { .op_tmpl =3D &info.primary_op_tmpl, - .primary_op_tmpl =3D SPI_MEM_OP(SPI_MEM_OP_CMD(nor->read_opcode, 0), - SPI_MEM_OP_ADDR(nor->addr_nbytes, 0, 0), - SPI_MEM_OP_DUMMY(nor->read_dummy, 0), - SPI_MEM_OP_DATA_IN(0, NULL, 0)), + .primary_op_tmpl =3D spi_nor_spimem_get_read_op(nor), .offset =3D 0, .length =3D nor->params->size, }; - struct spi_mem_op *op =3D info.op_tmpl; - - spi_nor_spimem_setup_op(nor, op, nor->read_proto); - - /* convert the dummy cycles to the number of bytes */ - op->dummy.nbytes =3D (nor->read_dummy * op->dummy.buswidth) / 8; - if (spi_nor_protocol_is_dtr(nor->read_proto)) - op->dummy.nbytes *=3D 2; - - /* - * Since spi_nor_spimem_setup_op() only sets buswidth when the number - * of data bytes is non-zero, the data buswidth won't be set here. So, - * do it explicitly. - */ - op->data.buswidth =3D spi_nor_get_protocol_data_nbits(nor->read_proto); =20 nor->dirmap.rdesc =3D devm_spi_mem_dirmap_create(nor->dev, nor->spimem, &info); --=20 2.34.1 From nobody Mon Jun 8 17:39:44 2026 Received: from SJ2PR03CU001.outbound.protection.outlook.com (mail-westusazon11012009.outbound.protection.outlook.com [52.101.43.9]) (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 B1F2C4534A2; Wed, 27 May 2026 17:56:54 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=52.101.43.9 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904616; cv=fail; b=uwQOlapdWYKa06BJVY6ZWIxkuc37wmED+xqLElQUq8q0c/L+tBP+fFfGkpco61tbCRH7I24JVH3mkvYzrnSIEkjUS796KPBdt+P7QaJDmysgalcO7zyMgrWAOP8edhGeY+VsmDLp7StoWc9lgAthsQswM9sIAohlUj0IGOwhzI0= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1779904616; c=relaxed/simple; bh=j7x4fhL5qBiEOu1RN81ffi2c/xYv1rD1g3jRS7KyS6w=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=Go01VDoxhQlHP7O5he8jQAkCZHm5BBvCWhs+PQHXS4symG/LfzjH9QvNmYXgEWCVcP47dZX8XkIi0T3VvquCZ1kGobsl3Sd6j6IG9Aqn3mEOlRnfKRArqeG6NTQlxnOF6iogw3YO4vL3mAHo6HWwu7mES0t4pMpfkB77dHuyChU= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com; spf=pass smtp.mailfrom=ti.com; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b=fiIm3uI0; arc=fail smtp.client-ip=52.101.43.9 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=ti.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=ti.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=ti.com header.i=@ti.com header.b="fiIm3uI0" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=TUupaBTKKm5M/D6aRIigzpmJFNtbQCm+EgknL/dFQyf+WDOtXOMLM5gxaqu17+Lu0m8hTPIAAk6UMIL6x3/PM3rNs6BBcGMEDUsnyrdbNt2iDr3WIkfN45Ncf8sa0iBxWRViXL5/yBSLeD2qjYiBYQWzer1kmNG1ircwY/tUyV4z/cX3loBedOJ84xH2cEVW1Tq0WgluVAnSspRWfcjYWyUwdeHCkcHuFK8pr0cC0HCOW/BzP7WX9J4nBwc8khh4BWrUE8NuT6MjnXEHxqzlYAQXsdaPCngUjhIfp/LG0pPk+JOa/sJmLQrn/43ceHSI8lsAbFVd4fXMK7wXkfe9aw== 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=LcSrydGSONihnxK+52dlm7a6KcXFBq+/rJkl7Fv7mWs=; b=uGRRlVgqtUlAsW7JASWtQUdt7A04vMW5YujGgDOFCkDpUIaYhd/gRvYzVmOqZAJk90+62ozR6FapIfvYVw6CfGajSC9AgZCesTM9lCZaP8ZjV+qlKuOId3+GBMR3nonxIp/d+bT6ReKcMb7dmWnk5Ds0CPIoF52Sw8cP9097MRmHS0M8BflcoTLXir1au7QyyN2qTXcBFn7Ipx7jIzmarQcC4DPCxjjtODOYS9JP6uLQdIPScsWXGR2Dq3mocB1VW0lXB5LC3f+WuqWxcm+PDkUhGjMPfGL2jl5j+M4hfK3UU5hbEFwwdXk7YHDXZpkyZu3DVNa+zN+dd/slT7cmiQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 198.47.21.195) smtp.rcpttodomain=lists.infradead.org smtp.mailfrom=ti.com; dmarc=pass (p=quarantine sp=none pct=100) action=none header.from=ti.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ti.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=LcSrydGSONihnxK+52dlm7a6KcXFBq+/rJkl7Fv7mWs=; b=fiIm3uI08mquooIZm/rSfEBzfyulnohw4Qqf5At+3h1HyhIuzyt2Wgya/F3CYcUkQtd+llA4ctjPQJyaMC9/HPmfZ27sd7VxiFjjXVMrLSEmmr7y9HamG1DbDvDHaclJaF/Bp4Pm82vRQw9uo7jfK88C9c+kSSA2M2sdDnt6u8U= Received: from MW4PR03CA0181.namprd03.prod.outlook.com (2603:10b6:303:b8::6) by SJ0PR10MB4573.namprd10.prod.outlook.com (2603:10b6:a03:2ac::23) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.13; Wed, 27 May 2026 17:56:52 +0000 Received: from CO1PEPF00012E61.namprd05.prod.outlook.com (2603:10b6:303:b8:cafe::43) by MW4PR03CA0181.outlook.office365.com (2603:10b6:303:b8::6) with Microsoft SMTP Server (version=TLS1_3, cipher=TLS_AES_256_GCM_SHA384) id 15.21.71.13 via Frontend Transport; Wed, 27 May 2026 17:56:52 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 198.47.21.195) smtp.mailfrom=ti.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=ti.com; Received-SPF: Pass (protection.outlook.com: domain of ti.com designates 198.47.21.195 as permitted sender) receiver=protection.outlook.com; client-ip=198.47.21.195; helo=flwvzet201.ext.ti.com; pr=C Received: from flwvzet201.ext.ti.com (198.47.21.195) by CO1PEPF00012E61.mail.protection.outlook.com (10.167.249.70) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.21.71.7 via Frontend Transport; Wed, 27 May 2026 17:56:50 +0000 Received: from DFLE202.ent.ti.com (10.64.6.60) by flwvzet201.ext.ti.com (10.248.192.32) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:46 -0500 Received: from DFLE206.ent.ti.com (10.64.6.64) by DFLE202.ent.ti.com (10.64.6.60) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37; Wed, 27 May 2026 12:56:45 -0500 Received: from lelvem-mr06.itg.ti.com (10.180.75.8) by DFLE206.ent.ti.com (10.64.6.64) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.2562.37 via Frontend Transport; Wed, 27 May 2026 12:56:45 -0500 Received: from santhoshkumark.dhcp.ti.com (santhoshkumark.dhcp.ti.com [172.24.233.254]) by lelvem-mr06.itg.ti.com (8.18.1/8.18.1) with ESMTP id 64RHtYpp4052476; Wed, 27 May 2026 12:56:41 -0500 From: Santhosh Kumar K To: , , , , , , , , , CC: , , , , , , , Subject: [PATCH v3 13/13] mtd: spi-nor: run PHY tuning after init and update dirmap frequency Date: Wed, 27 May 2026 23:25:27 +0530 Message-ID: <20260527175527.2247679-14-s-k6@ti.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20260527175527.2247679-1-s-k6@ti.com> References: <20260527175527.2247679-1-s-k6@ti.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-C2ProcessedOrg: 333ef613-75bf-4e12-a4b1-8e3623f5dcea X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: CO1PEPF00012E61:EE_|SJ0PR10MB4573:EE_ X-MS-Office365-Filtering-Correlation-Id: 396d73b4-b233-4502-2a33-08debc195464 X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|82310400026|36860700016|376014|1800799024|7416014|921020|6133799003|56012099006|3023799007|18002099003|22082099003; X-Microsoft-Antispam-Message-Info: G4ETrd+YcPvD7xvQJDSeJHpY+6Dn5rhLqgTHB2d3djaZNrKBVcJ3nIYv5vHfCWdTtFao+CEkwle65qQygxaHZUPbP9+DlHCkYHkeqhLX7IQNt3sTlcWd/VE7hkOEwnm8nA1YwLmNLGuSCq1bX1CGmPMCzQpHcQm1Kgbr680kF14Ml2OtFmi9v/96RFWmA1cPORnO877k4NQP4HcZ9a4m3e8sL5VZ1iHJkb7btrXsa26WZv4yq0UZ4SIJ3f+Hq8oLPkbx6WmBV+YlJqnxZAtsG4002RddCGjWjQn3MB9htGQ2hERG8iEH+z3IuSPnq+bz/xAT9ek7a6AJzWjuKnWG7J5WYUkYyrErgp7CYFqAtf6Tho5rF/y6JgpXT39GH22Ff+56xROLNBvdH6rYJ8xHSkMFj8IaMDn93DW5LxbVQ/GqwuXR4I8EZdJQFotda7vW7DsaioRWQ6J4ayx55AGWfn/Q5LurPIEbgqCUSpjODiWp8AqD2evycKbFPsXHBL3edVMuLpGotwPh2vYVSq6vbb8MULTnRtojGJUXmVENxAQzG+TM1km/E1A+41zIvDSAXsSrSFX8Zd+U69ahTzlzsssbohHWkfw5dJNDZ8+VXnPLHtVFU71jb0znzTBNVw3SZqITAm2wN+ZIKLmFElXcNKPVYDQCa51frEgBmIpaC8lGhbEW02/Na+yO79saAIzOlza8dk2yaTcwXmiwsvjhHLTvLoWt2jWVTAF+r9xTH34b+o5QNArgo8puIpo8ktfEUwWPPcLBrqwmPVIr0IxxpQ== X-Forefront-Antispam-Report: CIP:198.47.21.195;CTRY:US;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:flwvzet201.ext.ti.com;PTR:ErrorRetry;CAT:NONE;SFS:(13230040)(82310400026)(36860700016)(376014)(1800799024)(7416014)(921020)(6133799003)(56012099006)(3023799007)(18002099003)(22082099003);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData-ChunkCount: 1 X-MS-Exchange-AntiSpam-MessageData-0: BFPJHT0hc2SjcMdLPQ2XdMDduW+VjwxrIlvnvJW/PHpL4tS6kw0EJuuzOLngiD7pzEnZRy7aEwu1EvnnSlpvBWyTpIqZ4bfRGoe5A7+se+lyeIp2tHjYL30+SC7z7nagVZbpdm8CbCk5rSGemCz/N/8pzNEfg7bDrn8G3okSEbKxAKznCWkMPmGRqbIN4CKYjiDrn45o4E0cL3KxSIzsDIdcmfmldUX9Ldthck0VftBeMlI2dOzSj+PYkwkxzbTh8rKeWR/EObTCaMdLPGhFy2TCHm58txWIIcA4ELOwu3ENRcv5/egNX/yRaQCoeX02paFAkIiPTvhD8rc6NteQ5NM/E6DkrD2Wgm9amV+29xp1e3r87vHkd5AV0jIDdc70i0D4sAvnYkFCl5uG5b2gxLdYywzbiHtM3QhECmoyl+9rg/fabr/yP8yi2PBMerbT X-OriginatorOrg: ti.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 27 May 2026 17:56:50.7991 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 396d73b4-b233-4502-2a33-08debc195464 X-MS-Exchange-CrossTenant-Id: e5b49634-450b-4709-8abb-1e2b19b982b7 X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=e5b49634-450b-4709-8abb-1e2b19b982b7;Ip=[198.47.21.195];Helo=[flwvzet201.ext.ti.com] X-MS-Exchange-CrossTenant-AuthSource: CO1PEPF00012E61.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: SJ0PR10MB4573 Content-Type: text/plain; charset="utf-8" Introduce a persistent max_read_op field in struct spi_nor. Populate it with the correct op layout before creating the read dirmap so execute_tuning() receives a fully configured op. After both dirmaps are set up, run spi_mem_execute_tuning() to let the controller validate the read frequency and write it back into max_read_op.max_freq. Patch the dirmap's op template with this value so subsequent dirmap reads use the validated speed. spi_nor_spimem_get_read_op() is updated to propagate max_read_op.max_freq into every returned op, so non-dirmap reads via spi_nor_spimem_read_data() also benefit from the validated frequency automatically. Signed-off-by: Santhosh Kumar K --- drivers/mtd/spi-nor/core.c | 19 +++++++++++++++++++ include/linux/mtd/spi-nor.h | 3 +++ 2 files changed, 22 insertions(+) diff --git a/drivers/mtd/spi-nor/core.c b/drivers/mtd/spi-nor/core.c index 2c9859fb0794..207e0679549e 100644 --- a/drivers/mtd/spi-nor/core.c +++ b/drivers/mtd/spi-nor/core.c @@ -216,6 +216,9 @@ static struct spi_mem_op spi_nor_spimem_get_read_op(str= uct spi_nor *nor) if (spi_nor_protocol_is_dtr(nor->read_proto)) op.dummy.nbytes *=3D 2; =20 + /* Propagate the validated frequency; zero before tuning. */ + op.max_freq =3D nor->max_read_op.max_freq; + return op; } =20 @@ -3773,6 +3776,9 @@ static int spi_nor_probe(struct spi_mem *spimem) return -ENOMEM; } =20 + /* Populate the persistent template with the correct op layout for tuning= . */ + nor->max_read_op =3D spi_nor_spimem_get_read_op(nor); + ret =3D spi_nor_create_read_dirmap(nor); if (ret) return ret; @@ -3781,6 +3787,19 @@ static int spi_nor_probe(struct spi_mem *spimem) if (ret) return ret; =20 + /* Tuning failure is non-fatal; the device operates at base speed. */ + ret =3D spi_mem_execute_tuning(spimem, &nor->max_read_op, NULL); + if (ret && ret !=3D -EOPNOTSUPP) + dev_warn(dev, "Failed to execute PHY tuning: %d\n", ret); + + /* + * The dirmap was created before tuning ran; update its op template + * to use the validated frequency. + */ + if (!ret && nor->dirmap.rdesc) + nor->dirmap.rdesc->info.primary_op_tmpl.max_freq =3D + nor->max_read_op.max_freq; + return mtd_device_register(&nor->mtd, data ? data->parts : NULL, data ? data->nr_parts : 0); } diff --git a/include/linux/mtd/spi-nor.h b/include/linux/mtd/spi-nor.h index cdcfe0fd2e7d..6a11625f7b2d 100644 --- a/include/linux/mtd/spi-nor.h +++ b/include/linux/mtd/spi-nor.h @@ -419,6 +419,9 @@ struct spi_nor { struct spi_mem_dirmap_desc *wdesc; } dirmap; =20 + /* Persistent op template updated by execute_tuning with validated speed.= */ + struct spi_mem_op max_read_op; + void *priv; }; =20 --=20 2.34.1