1 // SPDX-License-Identifier: GPL-2.0+ 2 /* 3 * (C) Copyright 2021 Rockchip Electronics Co., Ltd 4 */ 5 6 #include <common.h> 7 #include <dm.h> 8 #include <dm/pinctrl.h> 9 #include <regmap.h> 10 #include <syscon.h> 11 12 #include "pinctrl-rockchip.h" 13 14 static int rk3588_set_mux(struct rockchip_pin_bank *bank, int pin, int mux) 15 { 16 struct rockchip_pinctrl_priv *priv = bank->priv; 17 struct regmap *regmap; 18 int iomux_num = (pin / 8); 19 int reg, ret, mask; 20 u8 bit; 21 u32 data; 22 23 debug("setting mux of GPIO%d-%d to %d\n", bank->bank_num, pin, mux); 24 25 regmap = priv->regmap_base; 26 reg = bank->iomux[iomux_num].offset; 27 if ((pin % 8) >= 4) 28 reg += 0x4; 29 bit = (pin % 4) * 4; 30 mask = 0xf; 31 32 if (bank->bank_num == 0) { 33 if ((pin >= RK_PB4) && (pin <= RK_PD7)) { 34 if (mux < 8) { 35 reg += 0x4000 - 0xC; /* PMU2_IOC_BASE */ 36 data = (mask << (bit + 16)); 37 data |= (mux & mask) << bit; 38 ret = regmap_write(regmap, reg, data); 39 } else { 40 u32 reg0 = 0; 41 42 reg0 = reg + 0x4000 - 0xC; /* PMU2_IOC_BASE */ 43 data = (mask << (bit + 16)); 44 data |= 8 << bit; 45 ret = regmap_write(regmap, reg0, data); 46 47 reg0 = reg + 0x8000; /* BUS_IOC_BASE */ 48 data = (mask << (bit + 16)); 49 data |= mux << bit; 50 regmap = priv->regmap_base; 51 regmap_write(regmap, reg0, data); 52 } 53 } else { 54 data = (mask << (bit + 16)); 55 data |= (mux & mask) << bit; 56 ret = regmap_write(regmap, reg, data); 57 } 58 return ret; 59 } else if (bank->bank_num > 0) { 60 reg += 0x8000; /* BUS_IOC_BASE */ 61 } 62 63 data = (mask << (bit + 16)); 64 data |= (mux & mask) << bit; 65 66 return regmap_write(regmap, reg, data); 67 } 68 69 #define rk3588_DRV_PMU_OFFSET 0x70 70 #define rk3588_DRV_GRF_OFFSET 0x200 71 #define rk3588_DRV_BITS_PER_PIN 8 72 #define rk3588_DRV_PINS_PER_REG 2 73 #define rk3588_DRV_BANK_STRIDE 0x40 74 75 #define PMU1_IOC_REG (0x0000) 76 #define PMU2_IOC_REG (0x4000) 77 #define BUS_IOC_REG (0x8000) 78 #define VCCIO1_4_IOC_REG (0x9000) 79 #define VCCIO3_5_IOC_REG (0xA000) 80 #define VCCIO2_IOC_REG (0xB000) 81 #define VCCIO6_IOC_REG (0xC000) 82 #define EMMC_IOC_REG (0xD000) 83 84 static const u32 rk3588_ds_regs[][2] = { 85 {RK_GPIO0_A0, PMU1_IOC_REG + 0x0010}, 86 {RK_GPIO0_A4, PMU1_IOC_REG + 0x0014}, 87 {RK_GPIO0_B0, PMU1_IOC_REG + 0x0018}, 88 {RK_GPIO0_B4, PMU2_IOC_REG + 0x0014}, 89 /* {RK_GPIO0_C0, PMU2_IOC_REG + 0x0018}, 90 {RK_GPIO0_C4, PMU2_IOC_REG + 0x001C}, 91 {RK_GPIO0_D0, PMU2_IOC_REG + 0x0020}, 92 {RK_GPIO0_D4, PMU2_IOC_REG + 0x0024},*/ 93 {RK_GPIO1_A0, VCCIO1_4_IOC_REG + 0x0020}, 94 /* {RK_GPIO1_A4, VCCIO1_4_IOC_REG + 0x0024}, 95 {RK_GPIO1_B0, VCCIO1_4_IOC_REG + 0x0028}, 96 {RK_GPIO1_B4, VCCIO1_4_IOC_REG + 0x002C}, 97 {RK_GPIO1_C0, VCCIO1_4_IOC_REG + 0x0030}, 98 {RK_GPIO1_C4, VCCIO1_4_IOC_REG + 0x0034}, 99 {RK_GPIO1_D0, VCCIO1_4_IOC_REG + 0x0038}, 100 {RK_GPIO1_D4, VCCIO1_4_IOC_REG + 0x003C},*/ 101 {RK_GPIO2_A0, EMMC_IOC_REG + 0x0040}, 102 /* {RK_GPIO2_A4, EMMC_IOC_REG + 0x0044}, 103 {RK_GPIO2_B0, EMMC_IOC_REG + 0x0048}, 104 {RK_GPIO2_B4, EMMC_IOC_REG + 0x004C}, 105 {RK_GPIO2_C0, EMMC_IOC_REG + 0x0050}, 106 {RK_GPIO2_C4, EMMC_IOC_REG + 0x0054}, 107 {RK_GPIO2_D0, EMMC_IOC_REG + 0x0058}, 108 {RK_GPIO2_D4, EMMC_IOC_REG + 0x005C},*/ 109 {RK_GPIO3_A0, VCCIO3_5_IOC_REG + 0x0060}, 110 /* {RK_GPIO3_A4, VCCIO3_5_IOC_REG + 0x0064}, 111 {RK_GPIO3_B0, VCCIO3_5_IOC_REG + 0x0068}, 112 {RK_GPIO3_B4, VCCIO3_5_IOC_REG + 0x006C}, 113 {RK_GPIO3_C0, VCCIO3_5_IOC_REG + 0x0070}, 114 {RK_GPIO3_C4, VCCIO3_5_IOC_REG + 0x0074}, 115 {RK_GPIO3_D0, VCCIO3_5_IOC_REG + 0x0078}, 116 {RK_GPIO3_D4, VCCIO3_5_IOC_REG + 0x007C},*/ 117 {RK_GPIO4_A0, VCCIO6_IOC_REG + 0x0080}, 118 /* {RK_GPIO4_A4, VCCIO6_IOC_REG + 0x0084}, 119 {RK_GPIO4_B0, VCCIO6_IOC_REG + 0x0088}, 120 {RK_GPIO4_B4, VCCIO6_IOC_REG + 0x008C}, 121 {RK_GPIO4_C0, VCCIO6_IOC_REG + 0x0090},*/ 122 }; 123 124 static const u32 rk3588_p_regs[][2] = { 125 {RK_GPIO0_A0, PMU1_IOC_REG + 0x0020}, 126 {RK_GPIO0_B0, PMU1_IOC_REG + 0x0024}, 127 {RK_GPIO0_B5, PMU2_IOC_REG + 0x0028}, 128 {RK_GPIO0_C0, PMU2_IOC_REG + 0x002C}, 129 {RK_GPIO0_D0, PMU2_IOC_REG + 0x0030}, 130 {RK_GPIO1_A0, VCCIO1_4_IOC_REG + 0x0110}, 131 /* {RK_GPIO1_B0, VCCIO1_4_IOC_REG + 0x0114}, 132 {RK_GPIO1_C0, VCCIO1_4_IOC_REG + 0x0118}, 133 {RK_GPIO1_D0, VCCIO1_4_IOC_REG + 0x011C},*/ 134 {RK_GPIO2_A0, EMMC_IOC_REG + 0x0120}, 135 /* {RK_GPIO2_D0, EMMC_IOC_REG + 0x012C},*/ 136 {RK_GPIO3_A0, VCCIO3_5_IOC_REG + 0x0130}, 137 /* {RK_GPIO3_B0, VCCIO3_5_IOC_REG + 0x0134}, 138 {RK_GPIO3_C0, VCCIO3_5_IOC_REG + 0x0138}, 139 {RK_GPIO3_D0, VCCIO3_5_IOC_REG + 0x013C},*/ 140 {RK_GPIO4_A0, VCCIO6_IOC_REG + 0x0140}, 141 /* {RK_GPIO4_B0, VCCIO6_IOC_REG + 0x0144}, 142 {RK_GPIO4_C0, VCCIO6_IOC_REG + 0x0148}, 143 {RK_GPIO4_D0, VCCIO2_IOC_REG + 0x014C},*/ 144 }; 145 146 static const u32 rk3588_smt_regs[][2] = { 147 {RK_GPIO0_A0, PMU1_IOC_REG + 0x0030}, 148 {RK_GPIO0_B0, PMU1_IOC_REG + 0x0034}, 149 {RK_GPIO0_B5, PMU2_IOC_REG + 0x0040}, 150 {RK_GPIO0_C0, PMU2_IOC_REG + 0x0044}, 151 {RK_GPIO0_D0, PMU2_IOC_REG + 0x0048}, 152 {RK_GPIO1_A0, VCCIO1_4_IOC_REG + 0x0210}, 153 /* {RK_GPIO1_B0, VCCIO1_4_IOC_REG + 0x0214}, 154 {RK_GPIO1_C0, VCCIO1_4_IOC_REG + 0x0218}, 155 {RK_GPIO1_D0, VCCIO1_4_IOC_REG + 0x021C},*/ 156 {RK_GPIO2_A0, EMMC_IOC_REG + 0x0220}, 157 {RK_GPIO2_D0, EMMC_IOC_REG + 0x022C}, 158 {RK_GPIO3_A0, VCCIO3_5_IOC_REG + 0x0230}, 159 /* {RK_GPIO3_B0, VCCIO3_5_IOC_REG + 0x0234}, 160 {RK_GPIO3_C0, VCCIO3_5_IOC_REG + 0x0238}, 161 {RK_GPIO3_D0, VCCIO3_5_IOC_REG + 0x023C},*/ 162 {RK_GPIO4_A0, VCCIO6_IOC_REG + 0x0240}, 163 /* {RK_GPIO4_B0, VCCIO6_IOC_REG + 0x0244}, 164 {RK_GPIO4_C0, VCCIO6_IOC_REG + 0x0248}, 165 {RK_GPIO4_D0, VCCIO2_IOC_REG + 0x024C},*/ 166 }; 167 168 #define RK3588_PULL_BITS_PER_PIN 2 169 #define RK3588_PULL_PINS_PER_REG 8 170 171 static void rk3588_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, 172 int pin_num, struct regmap **regmap, 173 int *reg, u8 *bit) 174 { 175 struct rockchip_pinctrl_priv *info = bank->priv; 176 u8 bank_num = bank->bank_num; 177 u32 pin = bank_num * 32 + pin_num; 178 int i; 179 180 for (i = ARRAY_SIZE(rk3588_p_regs) - 1; i >= 0; i--) { 181 if (pin >= rk3588_p_regs[i][0]) { 182 *reg = rk3588_p_regs[i][1]; 183 break; 184 } 185 BUG_ON(i == 0); 186 } 187 188 *regmap = info->regmap_base; 189 *reg += ((pin - rk3588_p_regs[i][0]) / RK3588_PULL_PINS_PER_REG) * 4; 190 *bit = pin_num % RK3588_PULL_PINS_PER_REG; 191 *bit *= RK3588_PULL_BITS_PER_PIN; 192 } 193 194 #define RK3588_DRV_BITS_PER_PIN 4 195 #define RK3588_DRV_PINS_PER_REG 4 196 197 static void rk3588_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, 198 int pin_num, struct regmap **regmap, 199 int *reg, u8 *bit) 200 { 201 struct rockchip_pinctrl_priv *info = bank->priv; 202 u8 bank_num = bank->bank_num; 203 u32 pin = bank_num * 32 + pin_num; 204 int i; 205 206 for (i = ARRAY_SIZE(rk3588_ds_regs) - 1; i >= 0; i--) { 207 if (pin >= rk3588_ds_regs[i][0]) { 208 *reg = rk3588_ds_regs[i][1]; 209 break; 210 } 211 BUG_ON(i == 0); 212 } 213 214 *regmap = info->regmap_base; 215 *reg += ((pin - rk3588_ds_regs[i][0]) / RK3588_DRV_PINS_PER_REG) * 4; 216 *bit = pin_num % RK3588_DRV_PINS_PER_REG; 217 *bit *= RK3588_DRV_BITS_PER_PIN; 218 } 219 220 #define RK3588_SMT_BITS_PER_PIN 1 221 #define RK3588_SMT_PINS_PER_REG 8 222 223 static int rk3588_calc_schmitt_reg_and_bit(struct rockchip_pin_bank *bank, 224 int pin_num, struct regmap **regmap, 225 int *reg, u8 *bit) 226 { 227 struct rockchip_pinctrl_priv *info = bank->priv; 228 u8 bank_num = bank->bank_num; 229 u32 pin = bank_num * 32 + pin_num; 230 int i; 231 232 for (i = ARRAY_SIZE(rk3588_smt_regs) - 1; i >= 0; i--) { 233 if (pin >= rk3588_smt_regs[i][0]) { 234 *reg = rk3588_smt_regs[i][1]; 235 break; 236 } 237 BUG_ON(i == 0); 238 } 239 240 *regmap = info->regmap_base; 241 *reg += ((pin - rk3588_smt_regs[i][0]) / RK3588_SMT_PINS_PER_REG) * 4; 242 *bit = pin_num % RK3588_SMT_PINS_PER_REG; 243 *bit *= RK3588_SMT_BITS_PER_PIN; 244 245 return 0; 246 } 247 248 static int rk3588_set_pull(struct rockchip_pin_bank *bank, 249 int pin_num, int pull) 250 { 251 struct regmap *regmap; 252 int reg; 253 u32 data; 254 u8 bit; 255 256 rk3588_calc_pull_reg_and_bit(bank, pin_num, ®map, ®, &bit); 257 258 /* enable the write to the equivalent lower bits */ 259 data = ((1 << ROCKCHIP_PULL_BITS_PER_PIN) - 1) << (bit + 16); 260 data |= (pull << bit); 261 262 return regmap_write(regmap, reg, data); 263 } 264 265 static int rk3588_set_drive(struct rockchip_pin_bank *bank, 266 int pin_num, int strength) 267 { 268 struct regmap *regmap; 269 int reg; 270 u32 data; 271 u8 bit; 272 273 rk3588_calc_drv_reg_and_bit(bank, pin_num, ®map, ®, &bit); 274 275 /* enable the write to the equivalent lower bits */ 276 data = ((1 << rk3588_DRV_BITS_PER_PIN) - 1) << (bit + 16); 277 data |= (strength << bit); 278 279 return regmap_write(regmap, reg, data); 280 } 281 282 static int rk3588_set_schmitt(struct rockchip_pin_bank *bank, 283 int pin_num, int enable) 284 { 285 struct regmap *regmap; 286 int reg; 287 u32 data; 288 u8 bit; 289 290 rk3588_calc_schmitt_reg_and_bit(bank, pin_num, ®map, ®, &bit); 291 292 /* enable the write to the equivalent lower bits */ 293 data = ((1 << RK3588_SMT_BITS_PER_PIN) - 1) << (bit + 16); 294 data |= (enable << bit); 295 296 return regmap_write(regmap, reg, data); 297 } 298 299 static struct rockchip_pin_bank rk3588_pin_banks[] = { 300 RK3588_PIN_BANK_FLAGS(0, 32, "gpio0", 301 IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY), 302 RK3588_PIN_BANK_FLAGS(1, 32, "gpio1", 303 IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY), 304 RK3588_PIN_BANK_FLAGS(2, 32, "gpio2", 305 IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY), 306 RK3588_PIN_BANK_FLAGS(3, 32, "gpio3", 307 IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY), 308 RK3588_PIN_BANK_FLAGS(4, 32, "gpio4", 309 IOMUX_WIDTH_4BIT, PULL_TYPE_IO_1V8_ONLY), 310 }; 311 312 static const struct rockchip_pin_ctrl rk3588_pin_ctrl = { 313 .pin_banks = rk3588_pin_banks, 314 .nr_banks = ARRAY_SIZE(rk3588_pin_banks), 315 .nr_pins = 160, 316 .set_mux = rk3588_set_mux, 317 .set_pull = rk3588_set_pull, 318 .set_drive = rk3588_set_drive, 319 .set_schmitt = rk3588_set_schmitt, 320 }; 321 322 static const struct udevice_id rk3588_pinctrl_ids[] = { 323 { 324 .compatible = "rockchip,rk3588-pinctrl", 325 .data = (ulong)&rk3588_pin_ctrl 326 }, 327 { } 328 }; 329 330 U_BOOT_DRIVER(pinctrl_rk3588) = { 331 .name = "rockchip_rk3588_pinctrl", 332 .id = UCLASS_PINCTRL, 333 .of_match = rk3588_pinctrl_ids, 334 .priv_auto_alloc_size = sizeof(struct rockchip_pinctrl_priv), 335 .ops = &rockchip_pinctrl_ops, 336 #if !CONFIG_IS_ENABLED(OF_PLATDATA) 337 .bind = dm_scan_fdt_dev, 338 #endif 339 .probe = rockchip_pinctrl_probe, 340 }; 341