xref: /rk3399_rockchip-uboot/drivers/pinctrl/rockchip/pinctrl-rk3588.c (revision b3bfcf592975f6c1113ff4879090e7a369bb026c)
136a14c2fSJianqun Xu // SPDX-License-Identifier: GPL-2.0+
236a14c2fSJianqun Xu /*
336a14c2fSJianqun Xu  * (C) Copyright 2021 Rockchip Electronics Co., Ltd
436a14c2fSJianqun Xu  */
536a14c2fSJianqun Xu 
636a14c2fSJianqun Xu #include <common.h>
736a14c2fSJianqun Xu #include <dm.h>
836a14c2fSJianqun Xu #include <dm/pinctrl.h>
936a14c2fSJianqun Xu #include <regmap.h>
1036a14c2fSJianqun Xu #include <syscon.h>
1136a14c2fSJianqun Xu 
1236a14c2fSJianqun Xu #include "pinctrl-rockchip.h"
1336a14c2fSJianqun Xu 
rk3588_set_mux(struct rockchip_pin_bank * bank,int pin,int mux)1436a14c2fSJianqun Xu static int rk3588_set_mux(struct rockchip_pin_bank *bank, int pin, int mux)
1536a14c2fSJianqun Xu {
1636a14c2fSJianqun Xu 	struct rockchip_pinctrl_priv *priv = bank->priv;
1736a14c2fSJianqun Xu 	struct regmap *regmap;
1836a14c2fSJianqun Xu 	int iomux_num = (pin / 8);
1936a14c2fSJianqun Xu 	int reg, ret, mask;
2036a14c2fSJianqun Xu 	u8 bit;
2136a14c2fSJianqun Xu 	u32 data;
2236a14c2fSJianqun Xu 
2336a14c2fSJianqun Xu 	debug("setting mux of GPIO%d-%d to %d\n", bank->bank_num, pin, mux);
2436a14c2fSJianqun Xu 
2536a14c2fSJianqun Xu 	regmap = priv->regmap_base;
2636a14c2fSJianqun Xu 	reg = bank->iomux[iomux_num].offset;
2736a14c2fSJianqun Xu 	if ((pin % 8) >= 4)
2836a14c2fSJianqun Xu 		reg += 0x4;
2936a14c2fSJianqun Xu 	bit = (pin % 4) * 4;
3036a14c2fSJianqun Xu 	mask = 0xf;
3136a14c2fSJianqun Xu 
3236a14c2fSJianqun Xu 	if (bank->bank_num == 0) {
3336a14c2fSJianqun Xu 		if ((pin >= RK_PB4) && (pin <= RK_PD7)) {
3436a14c2fSJianqun Xu 			if (mux < 8) {
35*b3bfcf59SJianqun Xu 				u32 reg0 = 0;
36*b3bfcf59SJianqun Xu 
37*b3bfcf59SJianqun Xu 				reg0 = reg + 0x4000 - 0xC; /* PMU2_IOC_BASE */
3836a14c2fSJianqun Xu 				data = (mask << (bit + 16));
3936a14c2fSJianqun Xu 				data |= (mux & mask) << bit;
40*b3bfcf59SJianqun Xu 				ret = regmap_write(regmap, reg0, data);
41*b3bfcf59SJianqun Xu 
42*b3bfcf59SJianqun Xu 				reg0 = reg + 0x8000; /* BUS_IOC_BASE */
43*b3bfcf59SJianqun Xu 				data = (mask << (bit + 16));
44*b3bfcf59SJianqun Xu 				regmap = priv->regmap_base;
45*b3bfcf59SJianqun Xu 				regmap_write(regmap, reg0, data);
4636a14c2fSJianqun Xu 			} else {
4736a14c2fSJianqun Xu 				u32 reg0 = 0;
4836a14c2fSJianqun Xu 
4936a14c2fSJianqun Xu 				reg0 = reg + 0x4000 - 0xC; /* PMU2_IOC_BASE */
5036a14c2fSJianqun Xu 				data = (mask << (bit + 16));
5136a14c2fSJianqun Xu 				data |= 8 << bit;
5236a14c2fSJianqun Xu 				ret = regmap_write(regmap, reg0, data);
5336a14c2fSJianqun Xu 
5436a14c2fSJianqun Xu 				reg0 = reg + 0x8000; /* BUS_IOC_BASE */
5536a14c2fSJianqun Xu 				data = (mask << (bit + 16));
5636a14c2fSJianqun Xu 				data |= mux << bit;
5736a14c2fSJianqun Xu 				regmap = priv->regmap_base;
5836a14c2fSJianqun Xu 				regmap_write(regmap, reg0, data);
5936a14c2fSJianqun Xu 			}
6036a14c2fSJianqun Xu 		} else {
6136a14c2fSJianqun Xu 			data = (mask << (bit + 16));
6236a14c2fSJianqun Xu 			data |= (mux & mask) << bit;
6336a14c2fSJianqun Xu 			ret = regmap_write(regmap, reg, data);
6436a14c2fSJianqun Xu 		}
6536a14c2fSJianqun Xu 		return ret;
6636a14c2fSJianqun Xu 	} else if (bank->bank_num > 0) {
6736a14c2fSJianqun Xu 		reg += 0x8000; /* BUS_IOC_BASE */
6836a14c2fSJianqun Xu 	}
6936a14c2fSJianqun Xu 
7036a14c2fSJianqun Xu 	data = (mask << (bit + 16));
7136a14c2fSJianqun Xu 	data |= (mux & mask) << bit;
7236a14c2fSJianqun Xu 
7336a14c2fSJianqun Xu 	return regmap_write(regmap, reg, data);
7436a14c2fSJianqun Xu }
7536a14c2fSJianqun Xu 
7636a14c2fSJianqun Xu #define rk3588_DRV_PMU_OFFSET		0x70
7736a14c2fSJianqun Xu #define rk3588_DRV_GRF_OFFSET		0x200
7836a14c2fSJianqun Xu #define rk3588_DRV_BITS_PER_PIN		8
7936a14c2fSJianqun Xu #define rk3588_DRV_PINS_PER_REG		2
8036a14c2fSJianqun Xu #define rk3588_DRV_BANK_STRIDE		0x40
8136a14c2fSJianqun Xu 
82038ebbd2SJianqun Xu #define RK3588_PMU1_IOC_REG		0x0000
83038ebbd2SJianqun Xu #define RK3588_PMU2_IOC_REG		0x4000
84038ebbd2SJianqun Xu #define RK3588_BUS_IOC_REG		0x8000
85038ebbd2SJianqun Xu #define RK3588_VCCIO1_4_IOC_REG		0x9000
86038ebbd2SJianqun Xu #define RK3588_VCCIO3_5_IOC_REG		0xA000
87038ebbd2SJianqun Xu #define RK3588_VCCIO2_IOC_REG		0xB000
88038ebbd2SJianqun Xu #define RK3588_VCCIO6_IOC_REG		0xC000
89038ebbd2SJianqun Xu #define RK3588_EMMC_IOC_REG		0xD000
9036a14c2fSJianqun Xu 
9136a14c2fSJianqun Xu static const u32 rk3588_ds_regs[][2] = {
92038ebbd2SJianqun Xu 	{ RK_GPIO0_A0, RK3588_PMU1_IOC_REG + 0x0010 },
93038ebbd2SJianqun Xu 	{ RK_GPIO0_A4, RK3588_PMU1_IOC_REG + 0x0014 },
94038ebbd2SJianqun Xu 	{ RK_GPIO0_B0, RK3588_PMU1_IOC_REG + 0x0018 },
95038ebbd2SJianqun Xu 	{ RK_GPIO0_B4, RK3588_PMU2_IOC_REG + 0x0014 },
96038ebbd2SJianqun Xu 	{ RK_GPIO0_C0, RK3588_PMU2_IOC_REG + 0x0018 },
97038ebbd2SJianqun Xu 	{ RK_GPIO0_C4, RK3588_PMU2_IOC_REG + 0x001C },
98038ebbd2SJianqun Xu 	{ RK_GPIO0_D0, RK3588_PMU2_IOC_REG + 0x0020 },
99038ebbd2SJianqun Xu 	{ RK_GPIO0_D4, RK3588_PMU2_IOC_REG + 0x0024 },
100038ebbd2SJianqun Xu 	{ RK_GPIO1_A0, RK3588_VCCIO1_4_IOC_REG + 0x0020 },
101038ebbd2SJianqun Xu 	{ RK_GPIO1_A4, RK3588_VCCIO1_4_IOC_REG + 0x0024 },
102038ebbd2SJianqun Xu 	{ RK_GPIO1_B0, RK3588_VCCIO1_4_IOC_REG + 0x0028 },
103038ebbd2SJianqun Xu 	{ RK_GPIO1_B4, RK3588_VCCIO1_4_IOC_REG + 0x002C },
104038ebbd2SJianqun Xu 	{ RK_GPIO1_C0, RK3588_VCCIO1_4_IOC_REG + 0x0030 },
105038ebbd2SJianqun Xu 	{ RK_GPIO1_C4, RK3588_VCCIO1_4_IOC_REG + 0x0034 },
106038ebbd2SJianqun Xu 	{ RK_GPIO1_D0, RK3588_VCCIO1_4_IOC_REG + 0x0038 },
107038ebbd2SJianqun Xu 	{ RK_GPIO1_D4, RK3588_VCCIO1_4_IOC_REG + 0x003C },
108038ebbd2SJianqun Xu 	{ RK_GPIO2_A0, RK3588_EMMC_IOC_REG + 0x0040 },
109038ebbd2SJianqun Xu 	{ RK_GPIO2_A4, RK3588_VCCIO3_5_IOC_REG + 0x0044 },
110038ebbd2SJianqun Xu 	{ RK_GPIO2_B0, RK3588_VCCIO3_5_IOC_REG + 0x0048 },
111038ebbd2SJianqun Xu 	{ RK_GPIO2_B4, RK3588_VCCIO3_5_IOC_REG + 0x004C },
112038ebbd2SJianqun Xu 	{ RK_GPIO2_C0, RK3588_VCCIO3_5_IOC_REG + 0x0050 },
113038ebbd2SJianqun Xu 	{ RK_GPIO2_C4, RK3588_VCCIO3_5_IOC_REG + 0x0054 },
114038ebbd2SJianqun Xu 	{ RK_GPIO2_D0, RK3588_EMMC_IOC_REG + 0x0058 },
115038ebbd2SJianqun Xu 	{ RK_GPIO2_D4, RK3588_EMMC_IOC_REG + 0x005C },
116038ebbd2SJianqun Xu 	{ RK_GPIO3_A0, RK3588_VCCIO3_5_IOC_REG + 0x0060 },
117038ebbd2SJianqun Xu 	{ RK_GPIO3_A4, RK3588_VCCIO3_5_IOC_REG + 0x0064 },
118038ebbd2SJianqun Xu 	{ RK_GPIO3_B0, RK3588_VCCIO3_5_IOC_REG + 0x0068 },
119038ebbd2SJianqun Xu 	{ RK_GPIO3_B4, RK3588_VCCIO3_5_IOC_REG + 0x006C },
120038ebbd2SJianqun Xu 	{ RK_GPIO3_C0, RK3588_VCCIO3_5_IOC_REG + 0x0070 },
121038ebbd2SJianqun Xu 	{ RK_GPIO3_C4, RK3588_VCCIO3_5_IOC_REG + 0x0074 },
122038ebbd2SJianqun Xu 	{ RK_GPIO3_D0, RK3588_VCCIO3_5_IOC_REG + 0x0078 },
123038ebbd2SJianqun Xu 	{ RK_GPIO3_D4, RK3588_VCCIO3_5_IOC_REG + 0x007C },
124038ebbd2SJianqun Xu 	{ RK_GPIO4_A0, RK3588_VCCIO6_IOC_REG + 0x0080 },
125038ebbd2SJianqun Xu 	{ RK_GPIO4_A4, RK3588_VCCIO6_IOC_REG + 0x0084 },
126038ebbd2SJianqun Xu 	{ RK_GPIO4_B0, RK3588_VCCIO6_IOC_REG + 0x0088 },
127038ebbd2SJianqun Xu 	{ RK_GPIO4_B4, RK3588_VCCIO6_IOC_REG + 0x008C },
128038ebbd2SJianqun Xu 	{ RK_GPIO4_C0, RK3588_VCCIO6_IOC_REG + 0x0090 },
129038ebbd2SJianqun Xu 	{ RK_GPIO4_C2, RK3588_VCCIO3_5_IOC_REG + 0x0090 },
130038ebbd2SJianqun Xu 	{ RK_GPIO4_C4, RK3588_VCCIO3_5_IOC_REG + 0x0094 },
131038ebbd2SJianqun Xu 	{ RK_GPIO4_D0, RK3588_VCCIO2_IOC_REG + 0x0098 },
13236a14c2fSJianqun Xu };
13336a14c2fSJianqun Xu 
13436a14c2fSJianqun Xu static const u32 rk3588_p_regs[][2] = {
135038ebbd2SJianqun Xu 	{ RK_GPIO0_A0, RK3588_PMU1_IOC_REG + 0x0020 },
136038ebbd2SJianqun Xu 	{ RK_GPIO0_B0, RK3588_PMU1_IOC_REG + 0x0024 },
137038ebbd2SJianqun Xu 	{ RK_GPIO0_B5, RK3588_PMU2_IOC_REG + 0x0028 },
138038ebbd2SJianqun Xu 	{ RK_GPIO0_C0, RK3588_PMU2_IOC_REG + 0x002C },
139038ebbd2SJianqun Xu 	{ RK_GPIO0_D0, RK3588_PMU2_IOC_REG + 0x0030 },
140038ebbd2SJianqun Xu 	{ RK_GPIO1_A0, RK3588_VCCIO1_4_IOC_REG + 0x0110 },
141038ebbd2SJianqun Xu 	{ RK_GPIO1_B0, RK3588_VCCIO1_4_IOC_REG + 0x0114 },
142038ebbd2SJianqun Xu 	{ RK_GPIO1_C0, RK3588_VCCIO1_4_IOC_REG + 0x0118 },
143038ebbd2SJianqun Xu 	{ RK_GPIO1_D0, RK3588_VCCIO1_4_IOC_REG + 0x011C },
144038ebbd2SJianqun Xu 	{ RK_GPIO2_A0, RK3588_EMMC_IOC_REG + 0x0120 },
145038ebbd2SJianqun Xu 	{ RK_GPIO2_A4, RK3588_VCCIO3_5_IOC_REG + 0x0120 },
146038ebbd2SJianqun Xu 	{ RK_GPIO2_B0, RK3588_VCCIO3_5_IOC_REG + 0x0124 },
147038ebbd2SJianqun Xu 	{ RK_GPIO2_C0, RK3588_VCCIO3_5_IOC_REG + 0x0128 },
148038ebbd2SJianqun Xu 	{ RK_GPIO2_D0, RK3588_EMMC_IOC_REG + 0x012C },
149038ebbd2SJianqun Xu 	{ RK_GPIO3_A0, RK3588_VCCIO3_5_IOC_REG + 0x0130 },
150038ebbd2SJianqun Xu 	{ RK_GPIO3_B0, RK3588_VCCIO3_5_IOC_REG + 0x0134 },
151038ebbd2SJianqun Xu 	{ RK_GPIO3_C0, RK3588_VCCIO3_5_IOC_REG + 0x0138 },
152038ebbd2SJianqun Xu 	{ RK_GPIO3_D0, RK3588_VCCIO3_5_IOC_REG + 0x013C },
153038ebbd2SJianqun Xu 	{ RK_GPIO4_A0, RK3588_VCCIO6_IOC_REG + 0x0140 },
154038ebbd2SJianqun Xu 	{ RK_GPIO4_B0, RK3588_VCCIO6_IOC_REG + 0x0144 },
155038ebbd2SJianqun Xu 	{ RK_GPIO4_C0, RK3588_VCCIO6_IOC_REG + 0x0148 },
156038ebbd2SJianqun Xu 	{ RK_GPIO4_C2, RK3588_VCCIO3_5_IOC_REG + 0x0148 },
157038ebbd2SJianqun Xu 	{ RK_GPIO4_D0, RK3588_VCCIO2_IOC_REG + 0x014C },
15836a14c2fSJianqun Xu };
15936a14c2fSJianqun Xu 
16036a14c2fSJianqun Xu static const u32 rk3588_smt_regs[][2] = {
161038ebbd2SJianqun Xu 	{ RK_GPIO0_A0, RK3588_PMU1_IOC_REG + 0x0030 },
162038ebbd2SJianqun Xu 	{ RK_GPIO0_B0, RK3588_PMU1_IOC_REG + 0x0034 },
163038ebbd2SJianqun Xu 	{ RK_GPIO0_B5, RK3588_PMU2_IOC_REG + 0x0040 },
164038ebbd2SJianqun Xu 	{ RK_GPIO0_C0, RK3588_PMU2_IOC_REG + 0x0044 },
165038ebbd2SJianqun Xu 	{ RK_GPIO0_D0, RK3588_PMU2_IOC_REG + 0x0048 },
166038ebbd2SJianqun Xu 	{ RK_GPIO1_A0, RK3588_VCCIO1_4_IOC_REG + 0x0210 },
167038ebbd2SJianqun Xu 	{ RK_GPIO1_B0, RK3588_VCCIO1_4_IOC_REG + 0x0214 },
168038ebbd2SJianqun Xu 	{ RK_GPIO1_C0, RK3588_VCCIO1_4_IOC_REG + 0x0218 },
169038ebbd2SJianqun Xu 	{ RK_GPIO1_D0, RK3588_VCCIO1_4_IOC_REG + 0x021C },
170038ebbd2SJianqun Xu 	{ RK_GPIO2_A0, RK3588_EMMC_IOC_REG + 0x0220 },
171038ebbd2SJianqun Xu 	{ RK_GPIO2_A4, RK3588_VCCIO3_5_IOC_REG + 0x0220 },
172038ebbd2SJianqun Xu 	{ RK_GPIO2_B0, RK3588_VCCIO3_5_IOC_REG + 0x0224 },
173038ebbd2SJianqun Xu 	{ RK_GPIO2_C0, RK3588_VCCIO3_5_IOC_REG + 0x0228 },
174038ebbd2SJianqun Xu 	{ RK_GPIO2_D0, RK3588_EMMC_IOC_REG + 0x022C },
175038ebbd2SJianqun Xu 	{ RK_GPIO3_A0, RK3588_VCCIO3_5_IOC_REG + 0x0230 },
176038ebbd2SJianqun Xu 	{ RK_GPIO3_B0, RK3588_VCCIO3_5_IOC_REG + 0x0234 },
177038ebbd2SJianqun Xu 	{ RK_GPIO3_C0, RK3588_VCCIO3_5_IOC_REG + 0x0238 },
178038ebbd2SJianqun Xu 	{ RK_GPIO3_D0, RK3588_VCCIO3_5_IOC_REG + 0x023C },
179038ebbd2SJianqun Xu 	{ RK_GPIO4_A0, RK3588_VCCIO6_IOC_REG + 0x0240 },
180038ebbd2SJianqun Xu 	{ RK_GPIO4_B0, RK3588_VCCIO6_IOC_REG + 0x0244 },
181038ebbd2SJianqun Xu 	{ RK_GPIO4_C0, RK3588_VCCIO6_IOC_REG + 0x0248 },
182038ebbd2SJianqun Xu 	{ RK_GPIO4_C2, RK3588_VCCIO3_5_IOC_REG + 0x0248 },
183038ebbd2SJianqun Xu 	{ RK_GPIO4_D0, RK3588_VCCIO2_IOC_REG + 0x024C },
18436a14c2fSJianqun Xu };
18536a14c2fSJianqun Xu 
18636a14c2fSJianqun Xu #define RK3588_PULL_BITS_PER_PIN		2
18736a14c2fSJianqun Xu #define RK3588_PULL_PINS_PER_REG		8
18836a14c2fSJianqun Xu 
rk3588_calc_pull_reg_and_bit(struct rockchip_pin_bank * bank,int pin_num,struct regmap ** regmap,int * reg,u8 * bit)18936a14c2fSJianqun Xu static void rk3588_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank,
19036a14c2fSJianqun Xu 					 int pin_num, struct regmap **regmap,
19136a14c2fSJianqun Xu 					 int *reg, u8 *bit)
19236a14c2fSJianqun Xu {
19336a14c2fSJianqun Xu 	struct rockchip_pinctrl_priv *info = bank->priv;
19436a14c2fSJianqun Xu 	u8 bank_num = bank->bank_num;
19536a14c2fSJianqun Xu 	u32 pin = bank_num * 32 + pin_num;
19636a14c2fSJianqun Xu 	int i;
19736a14c2fSJianqun Xu 
19836a14c2fSJianqun Xu 	for (i = ARRAY_SIZE(rk3588_p_regs) - 1; i >= 0; i--) {
19936a14c2fSJianqun Xu 		if (pin >= rk3588_p_regs[i][0]) {
20036a14c2fSJianqun Xu 			*reg = rk3588_p_regs[i][1];
20136a14c2fSJianqun Xu 			break;
20236a14c2fSJianqun Xu 		}
20336a14c2fSJianqun Xu 		BUG_ON(i == 0);
20436a14c2fSJianqun Xu 	}
20536a14c2fSJianqun Xu 
20636a14c2fSJianqun Xu 	*regmap = info->regmap_base;
20736a14c2fSJianqun Xu 	*reg += ((pin - rk3588_p_regs[i][0]) / RK3588_PULL_PINS_PER_REG) * 4;
20836a14c2fSJianqun Xu 	*bit = pin_num % RK3588_PULL_PINS_PER_REG;
20936a14c2fSJianqun Xu 	*bit *= RK3588_PULL_BITS_PER_PIN;
21036a14c2fSJianqun Xu }
21136a14c2fSJianqun Xu 
21236a14c2fSJianqun Xu #define RK3588_DRV_BITS_PER_PIN		4
21336a14c2fSJianqun Xu #define RK3588_DRV_PINS_PER_REG		4
21436a14c2fSJianqun Xu 
rk3588_calc_drv_reg_and_bit(struct rockchip_pin_bank * bank,int pin_num,struct regmap ** regmap,int * reg,u8 * bit)21536a14c2fSJianqun Xu static void rk3588_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank,
21636a14c2fSJianqun Xu 					int pin_num, struct regmap **regmap,
21736a14c2fSJianqun Xu 					int *reg, u8 *bit)
21836a14c2fSJianqun Xu {
21936a14c2fSJianqun Xu 	struct rockchip_pinctrl_priv *info = bank->priv;
22036a14c2fSJianqun Xu 	u8 bank_num = bank->bank_num;
22136a14c2fSJianqun Xu 	u32 pin = bank_num * 32 + pin_num;
22236a14c2fSJianqun Xu 	int i;
22336a14c2fSJianqun Xu 
22436a14c2fSJianqun Xu 	for (i = ARRAY_SIZE(rk3588_ds_regs) - 1; i >= 0; i--) {
22536a14c2fSJianqun Xu 		if (pin >= rk3588_ds_regs[i][0]) {
22636a14c2fSJianqun Xu 			*reg = rk3588_ds_regs[i][1];
22736a14c2fSJianqun Xu 			break;
22836a14c2fSJianqun Xu 		}
22936a14c2fSJianqun Xu 		BUG_ON(i == 0);
23036a14c2fSJianqun Xu 	}
23136a14c2fSJianqun Xu 
23236a14c2fSJianqun Xu 	*regmap = info->regmap_base;
23336a14c2fSJianqun Xu 	*reg += ((pin - rk3588_ds_regs[i][0]) / RK3588_DRV_PINS_PER_REG) * 4;
23436a14c2fSJianqun Xu 	*bit = pin_num % RK3588_DRV_PINS_PER_REG;
23536a14c2fSJianqun Xu 	*bit *= RK3588_DRV_BITS_PER_PIN;
23636a14c2fSJianqun Xu }
23736a14c2fSJianqun Xu 
23836a14c2fSJianqun Xu #define RK3588_SMT_BITS_PER_PIN		1
239504ca0d4SJianqun Xu #define RK3588_SMT_PINS_PER_REG		8
24036a14c2fSJianqun Xu 
rk3588_calc_schmitt_reg_and_bit(struct rockchip_pin_bank * bank,int pin_num,struct regmap ** regmap,int * reg,u8 * bit)24136a14c2fSJianqun Xu static int rk3588_calc_schmitt_reg_and_bit(struct rockchip_pin_bank *bank,
24236a14c2fSJianqun Xu 					   int pin_num, struct regmap **regmap,
24336a14c2fSJianqun Xu 					   int *reg, u8 *bit)
24436a14c2fSJianqun Xu {
24536a14c2fSJianqun Xu 	struct rockchip_pinctrl_priv *info = bank->priv;
24636a14c2fSJianqun Xu 	u8 bank_num = bank->bank_num;
24736a14c2fSJianqun Xu 	u32 pin = bank_num * 32 + pin_num;
24836a14c2fSJianqun Xu 	int i;
24936a14c2fSJianqun Xu 
25036a14c2fSJianqun Xu 	for (i = ARRAY_SIZE(rk3588_smt_regs) - 1; i >= 0; i--) {
25136a14c2fSJianqun Xu 		if (pin >= rk3588_smt_regs[i][0]) {
25236a14c2fSJianqun Xu 			*reg = rk3588_smt_regs[i][1];
25336a14c2fSJianqun Xu 			break;
25436a14c2fSJianqun Xu 		}
25536a14c2fSJianqun Xu 		BUG_ON(i == 0);
25636a14c2fSJianqun Xu 	}
25736a14c2fSJianqun Xu 
25836a14c2fSJianqun Xu 	*regmap = info->regmap_base;
25936a14c2fSJianqun Xu 	*reg += ((pin - rk3588_smt_regs[i][0]) / RK3588_SMT_PINS_PER_REG) * 4;
26036a14c2fSJianqun Xu 	*bit = pin_num % RK3588_SMT_PINS_PER_REG;
26136a14c2fSJianqun Xu 	*bit *= RK3588_SMT_BITS_PER_PIN;
26236a14c2fSJianqun Xu 
26336a14c2fSJianqun Xu 	return 0;
26436a14c2fSJianqun Xu }
26536a14c2fSJianqun Xu 
rk3588_set_pull(struct rockchip_pin_bank * bank,int pin_num,int pull)26636a14c2fSJianqun Xu static int rk3588_set_pull(struct rockchip_pin_bank *bank,
26736a14c2fSJianqun Xu 			   int pin_num, int pull)
26836a14c2fSJianqun Xu {
26936a14c2fSJianqun Xu 	struct regmap *regmap;
27036a14c2fSJianqun Xu 	int reg;
27136a14c2fSJianqun Xu 	u32 data;
27236a14c2fSJianqun Xu 	u8 bit;
27336a14c2fSJianqun Xu 
27436a14c2fSJianqun Xu 	rk3588_calc_pull_reg_and_bit(bank, pin_num, &regmap, &reg, &bit);
27536a14c2fSJianqun Xu 
27636a14c2fSJianqun Xu 	/* enable the write to the equivalent lower bits */
27736a14c2fSJianqun Xu 	data = ((1 << ROCKCHIP_PULL_BITS_PER_PIN) - 1) << (bit + 16);
27836a14c2fSJianqun Xu 	data |= (pull << bit);
27936a14c2fSJianqun Xu 
28036a14c2fSJianqun Xu 	return regmap_write(regmap, reg, data);
28136a14c2fSJianqun Xu }
28236a14c2fSJianqun Xu 
rk3588_set_drive(struct rockchip_pin_bank * bank,int pin_num,int strength)28336a14c2fSJianqun Xu static int rk3588_set_drive(struct rockchip_pin_bank *bank,
28436a14c2fSJianqun Xu 			    int pin_num, int strength)
28536a14c2fSJianqun Xu {
28636a14c2fSJianqun Xu 	struct regmap *regmap;
28736a14c2fSJianqun Xu 	int reg;
28836a14c2fSJianqun Xu 	u32 data;
28936a14c2fSJianqun Xu 	u8 bit;
29036a14c2fSJianqun Xu 
29136a14c2fSJianqun Xu 	rk3588_calc_drv_reg_and_bit(bank, pin_num, &regmap, &reg, &bit);
29236a14c2fSJianqun Xu 
29336a14c2fSJianqun Xu 	/* enable the write to the equivalent lower bits */
29436a14c2fSJianqun Xu 	data = ((1 << rk3588_DRV_BITS_PER_PIN) - 1) << (bit + 16);
29536a14c2fSJianqun Xu 	data |= (strength << bit);
29636a14c2fSJianqun Xu 
29736a14c2fSJianqun Xu 	return regmap_write(regmap, reg, data);
29836a14c2fSJianqun Xu }
29936a14c2fSJianqun Xu 
rk3588_set_schmitt(struct rockchip_pin_bank * bank,int pin_num,int enable)30036a14c2fSJianqun Xu static int rk3588_set_schmitt(struct rockchip_pin_bank *bank,
30136a14c2fSJianqun Xu 			      int pin_num, int enable)
30236a14c2fSJianqun Xu {
30336a14c2fSJianqun Xu 	struct regmap *regmap;
30436a14c2fSJianqun Xu 	int reg;
30536a14c2fSJianqun Xu 	u32 data;
30636a14c2fSJianqun Xu 	u8 bit;
30736a14c2fSJianqun Xu 
30836a14c2fSJianqun Xu 	rk3588_calc_schmitt_reg_and_bit(bank, pin_num, &regmap, &reg, &bit);
30936a14c2fSJianqun Xu 
31036a14c2fSJianqun Xu 	/* enable the write to the equivalent lower bits */
31136a14c2fSJianqun Xu 	data = ((1 << RK3588_SMT_BITS_PER_PIN) - 1) << (bit + 16);
31236a14c2fSJianqun Xu 	data |= (enable << bit);
31336a14c2fSJianqun Xu 
31436a14c2fSJianqun Xu 	return regmap_write(regmap, reg, data);
31536a14c2fSJianqun Xu }
31636a14c2fSJianqun Xu 
31736a14c2fSJianqun Xu static struct rockchip_pin_bank rk3588_pin_banks[] = {
31836a14c2fSJianqun Xu 	RK3588_PIN_BANK_FLAGS(0, 32, "gpio0",
31936a14c2fSJianqun Xu 			      IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY),
32036a14c2fSJianqun Xu 	RK3588_PIN_BANK_FLAGS(1, 32, "gpio1",
32136a14c2fSJianqun Xu 			      IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY),
32236a14c2fSJianqun Xu 	RK3588_PIN_BANK_FLAGS(2, 32, "gpio2",
32336a14c2fSJianqun Xu 			      IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY),
32436a14c2fSJianqun Xu 	RK3588_PIN_BANK_FLAGS(3, 32, "gpio3",
32536a14c2fSJianqun Xu 			      IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY),
32636a14c2fSJianqun Xu 	RK3588_PIN_BANK_FLAGS(4, 32, "gpio4",
32736a14c2fSJianqun Xu 			      IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY),
32836a14c2fSJianqun Xu };
32936a14c2fSJianqun Xu 
33036a14c2fSJianqun Xu static const struct rockchip_pin_ctrl rk3588_pin_ctrl = {
33136a14c2fSJianqun Xu 	.pin_banks		= rk3588_pin_banks,
33236a14c2fSJianqun Xu 	.nr_banks		= ARRAY_SIZE(rk3588_pin_banks),
33336a14c2fSJianqun Xu 	.nr_pins		= 160,
33436a14c2fSJianqun Xu 	.set_mux		= rk3588_set_mux,
33536a14c2fSJianqun Xu 	.set_pull		= rk3588_set_pull,
33636a14c2fSJianqun Xu 	.set_drive		= rk3588_set_drive,
33736a14c2fSJianqun Xu 	.set_schmitt		= rk3588_set_schmitt,
33836a14c2fSJianqun Xu };
33936a14c2fSJianqun Xu 
34036a14c2fSJianqun Xu static const struct udevice_id rk3588_pinctrl_ids[] = {
34136a14c2fSJianqun Xu 	{
34236a14c2fSJianqun Xu 		.compatible = "rockchip,rk3588-pinctrl",
34336a14c2fSJianqun Xu 		.data = (ulong)&rk3588_pin_ctrl
34436a14c2fSJianqun Xu 	},
34536a14c2fSJianqun Xu 	{ }
34636a14c2fSJianqun Xu };
34736a14c2fSJianqun Xu 
34836a14c2fSJianqun Xu U_BOOT_DRIVER(pinctrl_rk3588) = {
34936a14c2fSJianqun Xu 	.name		= "rockchip_rk3588_pinctrl",
35036a14c2fSJianqun Xu 	.id		= UCLASS_PINCTRL,
35136a14c2fSJianqun Xu 	.of_match	= rk3588_pinctrl_ids,
35236a14c2fSJianqun Xu 	.priv_auto_alloc_size = sizeof(struct rockchip_pinctrl_priv),
35336a14c2fSJianqun Xu 	.ops		= &rockchip_pinctrl_ops,
35436a14c2fSJianqun Xu #if !CONFIG_IS_ENABLED(OF_PLATDATA)
35536a14c2fSJianqun Xu 	.bind		= dm_scan_fdt_dev,
35636a14c2fSJianqun Xu #endif
35736a14c2fSJianqun Xu 	.probe		= rockchip_pinctrl_probe,
35836a14c2fSJianqun Xu };
359