1 /*
2 * Copyright (c) 2021-2023 IoT.bzh
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 *
6 */
7
8 #define DT_DRV_COMPAT renesas_rcar_pfc
9
10 #include "pfc_rcar.h"
11 #include <zephyr/arch/cpu.h>
12 #include <zephyr/devicetree.h>
13 #include <zephyr/drivers/pinctrl.h>
14 #include <zephyr/init.h>
15 #include <zephyr/sys/util.h>
16 #include <zephyr/sys/device_mmio.h>
17
18 #define PFC_RCAR_PMMR 0x0
19
20 /* Gen3 only has one base address, Gen4 has one per GPIO controller */
21 #if defined(CONFIG_SOC_SERIES_RCAR_GEN3)
22 #define PFC_RCAR_GPSR 0x100
23 #define PFC_RCAR_IPSR 0x200
24 #elif defined(CONFIG_SOC_SERIES_RCAR_GEN4)
25 #define PFC_RCAR_GPSR 0x040
26 #define PFC_RCAR_IPSR 0x060
27 #else
28 #error Unsupported SoC Series
29 #endif
30
31 /* swap both arguments */
32 #define PFC_REG_ADDRESS(idx, inst) DT_INST_REG_ADDR_BY_IDX(inst, idx)
33 static uintptr_t reg_base[] = {
34 LISTIFY(DT_NUM_REGS(DT_DRV_INST(0)), PFC_REG_ADDRESS, (,), 0)
35 };
36
37 #define PFC_REG_SIZE(idx, inst) DT_INST_REG_SIZE_BY_IDX(inst, idx)
38 static const uintptr_t __maybe_unused reg_sizes[] = {
39 LISTIFY(DT_NUM_REGS(DT_DRV_INST(0)), PFC_REG_SIZE, (,), 0)
40 };
41
42 #ifdef CONFIG_PINCTRL_RCAR_VOLTAGE_CONTROL
43 /* POC Control Register can control IO voltage level that is supplied to the pin */
44 struct pfc_pocctrl_reg {
45 uint32_t offset;
46 const uint16_t pins[32];
47 };
48 #endif /* CONFIG_PINCTRL_RCAR_VOLTAGE_CONTROL */
49
50 /*
51 * Each drive step is either encoded in 2 or 3 bits.
52 * So based on a 24 mA maximum value each step is either
53 * 24/4 mA or 24/8 mA.
54 */
55 #define PFC_RCAR_DRIVE_MAX 24U
56 #define PFC_RCAR_DRIVE_STEP(size) \
57 (size == 2 ? PFC_RCAR_DRIVE_MAX / 4 : PFC_RCAR_DRIVE_MAX / 8)
58
59 /* Some registers such as IPSR GPSR or DRVCTRL are protected and
60 * must be preceded to a write to PMMR with the inverse value.
61 */
pfc_rcar_write(uintptr_t pfc_base,uint32_t offs,uint32_t val)62 static void pfc_rcar_write(uintptr_t pfc_base, uint32_t offs, uint32_t val)
63 {
64 sys_write32(~val, pfc_base + PFC_RCAR_PMMR);
65 sys_write32(val, pfc_base + offs);
66 }
67
68 /* Set the pin either in gpio or peripheral */
pfc_rcar_set_gpsr(uintptr_t pfc_base,uint16_t pin,bool peripheral)69 static void pfc_rcar_set_gpsr(uintptr_t pfc_base,
70 uint16_t pin, bool peripheral)
71 {
72 #if defined(CONFIG_SOC_SERIES_RCAR_GEN3)
73 /* On Gen3 we have multiple GPSR at one base address */
74 uint8_t bank = pin / 32;
75 #elif defined(CONFIG_SOC_SERIES_RCAR_GEN4)
76 /* On Gen4 we have one GPSR at multiple base address */
77 uint8_t bank = 0;
78 #endif
79 uint8_t bit = pin % 32;
80 uint32_t val = sys_read32(pfc_base + PFC_RCAR_GPSR +
81 bank * sizeof(uint32_t));
82
83 if (peripheral) {
84 val |= BIT(bit);
85 } else {
86 val &= ~BIT(bit);
87 }
88 pfc_rcar_write(pfc_base, PFC_RCAR_GPSR + bank * sizeof(uint32_t), val);
89 }
90
91 /* Set peripheral function */
pfc_rcar_set_ipsr(uintptr_t pfc_base,const struct rcar_pin_func * rcar_func)92 static void pfc_rcar_set_ipsr(uintptr_t pfc_base,
93 const struct rcar_pin_func *rcar_func)
94 {
95 uint16_t reg_offs = PFC_RCAR_IPSR + rcar_func->bank * sizeof(uint32_t);
96 uint32_t val = sys_read32(pfc_base + reg_offs);
97
98 val &= ~(0xFU << rcar_func->shift);
99 val |= (rcar_func->func << rcar_func->shift);
100 pfc_rcar_write(pfc_base, reg_offs, val);
101 }
102
pfc_rcar_get_drive_reg(uint16_t pin,uint8_t * offset,uint8_t * size)103 static uint32_t pfc_rcar_get_drive_reg(uint16_t pin, uint8_t *offset,
104 uint8_t *size)
105 {
106 const struct pfc_drive_reg *drive_regs = pfc_rcar_get_drive_regs();
107
108 while (drive_regs->reg != 0U) {
109 for (size_t i = 0U; i < ARRAY_SIZE(drive_regs->fields); i++) {
110 if (drive_regs->fields[i].pin == pin) {
111 *offset = drive_regs->fields[i].offset;
112 *size = drive_regs->fields[i].size;
113 return drive_regs->reg;
114 }
115 }
116 drive_regs++;
117 }
118
119 return 0;
120 }
121
122 /*
123 * Maximum drive strength is 24mA. This value can be lowered
124 * using DRVCTRLx registers, some pins have 8 steps (3 bits size encoded)
125 * some have 4 steps (2 bits size encoded).
126 */
pfc_rcar_set_drive_strength(uintptr_t pfc_base,uint16_t pin,uint8_t strength)127 static int pfc_rcar_set_drive_strength(uintptr_t pfc_base, uint16_t pin,
128 uint8_t strength)
129 {
130 uint8_t offset, size, step;
131 uint32_t reg, val;
132
133 reg = pfc_rcar_get_drive_reg(pin, &offset, &size);
134 if (reg == 0U) {
135 return -EINVAL;
136 }
137
138 step = PFC_RCAR_DRIVE_STEP(size);
139 if ((strength < step) || (strength > PFC_RCAR_DRIVE_MAX)) {
140 return -EINVAL;
141 }
142
143 /* Convert the value from mA based on a full drive strength
144 * value of 24mA.
145 */
146 strength = (strength / step) - 1U;
147 /* clear previous drive strength value */
148 val = sys_read32(pfc_base + reg);
149 val &= ~GENMASK(offset + size - 1U, offset);
150 val |= strength << offset;
151
152 pfc_rcar_write(pfc_base, reg, val);
153
154 return 0;
155 }
156
pfc_rcar_get_bias_reg(uint16_t pin,uint8_t * bit)157 static const struct pfc_bias_reg *pfc_rcar_get_bias_reg(uint16_t pin,
158 uint8_t *bit)
159 {
160 const struct pfc_bias_reg *bias_regs = pfc_rcar_get_bias_regs();
161
162 /* Loop around all the registers to find the bit for a given pin */
163 while (bias_regs->puen && bias_regs->pud) {
164 for (size_t i = 0U; i < ARRAY_SIZE(bias_regs->pins); i++) {
165 if (bias_regs->pins[i] == pin) {
166 *bit = i;
167 return bias_regs;
168 }
169 }
170 bias_regs++;
171 }
172
173 return NULL;
174 }
175
pfc_rcar_set_bias(uintptr_t pfc_base,uint16_t pin,uint16_t flags)176 int pfc_rcar_set_bias(uintptr_t pfc_base, uint16_t pin, uint16_t flags)
177 {
178 uint32_t val;
179 uint8_t bit;
180 const struct pfc_bias_reg *bias_reg = pfc_rcar_get_bias_reg(pin, &bit);
181
182 if (bias_reg == NULL) {
183 return -EINVAL;
184 }
185
186 /* pull enable/disable*/
187 val = sys_read32(pfc_base + bias_reg->puen);
188 if ((flags & RCAR_PIN_FLAGS_PUEN) == 0U) {
189 sys_write32(val & ~BIT(bit), pfc_base + bias_reg->puen);
190 return 0;
191 }
192 sys_write32(val | BIT(bit), pfc_base + bias_reg->puen);
193
194 /* pull - up/down */
195 val = sys_read32(pfc_base + bias_reg->pud);
196 if (flags & RCAR_PIN_FLAGS_PUD) {
197 sys_write32(val | BIT(bit), pfc_base + bias_reg->pud);
198 } else {
199 sys_write32(val & ~BIT(bit), pfc_base + bias_reg->pud);
200 }
201 return 0;
202 }
203
204 #ifdef CONFIG_PINCTRL_RCAR_VOLTAGE_CONTROL
205
206 const struct pfc_pocctrl_reg pfc_r8a77951_r8a77961_volt_regs[] = {
207 {
208 .offset = 0x0380,
209 .pins = {
210 [0] = RCAR_GP_PIN(3, 0), /* SD0_CLK */
211 [1] = RCAR_GP_PIN(3, 1), /* SD0_CMD */
212 [2] = RCAR_GP_PIN(3, 2), /* SD0_DAT0 */
213 [3] = RCAR_GP_PIN(3, 3), /* SD0_DAT1 */
214 [4] = RCAR_GP_PIN(3, 4), /* SD0_DAT2 */
215 [5] = RCAR_GP_PIN(3, 5), /* SD0_DAT3 */
216 [6] = RCAR_GP_PIN(3, 6), /* SD1_CLK */
217 [7] = RCAR_GP_PIN(3, 7), /* SD1_CMD */
218 [8] = RCAR_GP_PIN(3, 8), /* SD1_DAT0 */
219 [9] = RCAR_GP_PIN(3, 9), /* SD1_DAT1 */
220 [10] = RCAR_GP_PIN(3, 10), /* SD1_DAT2 */
221 [11] = RCAR_GP_PIN(3, 11), /* SD1_DAT3 */
222 [12] = RCAR_GP_PIN(4, 0), /* SD2_CLK */
223 [13] = RCAR_GP_PIN(4, 1), /* SD2_CMD */
224 [14] = RCAR_GP_PIN(4, 2), /* SD2_DAT0 */
225 [15] = RCAR_GP_PIN(4, 3), /* SD2_DAT1 */
226 [16] = RCAR_GP_PIN(4, 4), /* SD2_DAT2 */
227 [17] = RCAR_GP_PIN(4, 5), /* SD2_DAT3 */
228 [18] = RCAR_GP_PIN(4, 6), /* SD2_DS */
229 [19] = RCAR_GP_PIN(4, 7), /* SD3_CLK */
230 [20] = RCAR_GP_PIN(4, 8), /* SD3_CMD */
231 [21] = RCAR_GP_PIN(4, 9), /* SD3_DAT0 */
232 [22] = RCAR_GP_PIN(4, 10), /* SD3_DAT1 */
233 [23] = RCAR_GP_PIN(4, 11), /* SD3_DAT2 */
234 [24] = RCAR_GP_PIN(4, 12), /* SD3_DAT3 */
235 [25] = RCAR_GP_PIN(4, 13), /* SD3_DAT4 */
236 [26] = RCAR_GP_PIN(4, 14), /* SD3_DAT5 */
237 [27] = RCAR_GP_PIN(4, 15), /* SD3_DAT6 */
238 [28] = RCAR_GP_PIN(4, 16), /* SD3_DAT7 */
239 [29] = RCAR_GP_PIN(4, 17), /* SD3_DS */
240 [30] = -1,
241 [31] = -1,
242 }
243 },
244 { /* sentinel */ },
245 };
246
pfc_rcar_get_io_voltage_regs(void)247 static const struct pfc_pocctrl_reg *pfc_rcar_get_io_voltage_regs(void)
248 {
249 return pfc_r8a77951_r8a77961_volt_regs;
250 }
251
pfc_rcar_get_pocctrl_reg(uint16_t pin,uint8_t * bit)252 static const struct pfc_pocctrl_reg *pfc_rcar_get_pocctrl_reg(uint16_t pin, uint8_t *bit)
253 {
254 const struct pfc_pocctrl_reg *voltage_regs = pfc_rcar_get_io_voltage_regs();
255
256 BUILD_ASSERT(ARRAY_SIZE(voltage_regs->pins) < UINT8_MAX);
257
258 /* Loop around all the registers to find the bit for a given pin */
259 while (voltage_regs && voltage_regs->offset) {
260 uint8_t i;
261
262 for (i = 0U; i < ARRAY_SIZE(voltage_regs->pins); i++) {
263 if (voltage_regs->pins[i] == pin) {
264 *bit = i;
265 return voltage_regs;
266 }
267 }
268 voltage_regs++;
269 }
270
271 return NULL;
272 }
273
pfc_rcar_set_voltage(uintptr_t pfc_base,uint16_t pin,uint16_t voltage)274 static void pfc_rcar_set_voltage(uintptr_t pfc_base, uint16_t pin, uint16_t voltage)
275 {
276 uint32_t val;
277 uint8_t bit;
278 const struct pfc_pocctrl_reg *voltage_reg;
279
280 voltage_reg = pfc_rcar_get_pocctrl_reg(pin, &bit);
281 if (!voltage_reg) {
282 return;
283 }
284
285 val = sys_read32(pfc_base + voltage_reg->offset);
286
287 switch (voltage) {
288 case PIN_VOLTAGE_1P8V:
289 if (!(val & BIT(bit))) {
290 return;
291 }
292 val &= ~BIT(bit);
293 break;
294 case PIN_VOLTAGE_3P3V:
295 if (val & BIT(bit)) {
296 return;
297 }
298 val |= BIT(bit);
299 break;
300 default:
301 break;
302 }
303
304 pfc_rcar_write(pfc_base, voltage_reg->offset, val);
305 }
306 #endif /* CONFIG_PINCTRL_RCAR_VOLTAGE_CONTROL */
307
pinctrl_configure_pin(const pinctrl_soc_pin_t * pin)308 int pinctrl_configure_pin(const pinctrl_soc_pin_t *pin)
309 {
310 int ret = 0;
311 uint8_t reg_index;
312 uintptr_t pfc_base;
313
314 ret = pfc_rcar_get_reg_index(pin->pin, ®_index);
315 if (ret) {
316 return ret;
317 }
318
319 if (reg_index >= ARRAY_SIZE(reg_base)) {
320 return -EINVAL;
321 }
322
323 pfc_base = reg_base[reg_index];
324
325 /* Set pin as GPIO if capable */
326 if (RCAR_IS_GP_PIN(pin->pin)) {
327 pfc_rcar_set_gpsr(pfc_base, pin->pin, false);
328 } else if ((pin->flags & RCAR_PIN_FLAGS_FUNC_SET) == 0U) {
329 /* A function must be set for non GPIO capable pin */
330 return -EINVAL;
331 }
332
333 #ifdef CONFIG_PINCTRL_RCAR_VOLTAGE_CONTROL
334 if (pin->voltage != PIN_VOLTAGE_NONE) {
335 pfc_rcar_set_voltage(pfc_base, pin->pin, pin->voltage);
336 }
337 #endif
338
339 /* Select function for pin */
340 if ((pin->flags & RCAR_PIN_FLAGS_FUNC_SET) != 0U) {
341
342 if ((pin->flags & RCAR_PIN_FLAGS_FUNC_DUMMY) == 0U) {
343 pfc_rcar_set_ipsr(pfc_base, &pin->func);
344 }
345
346 if (RCAR_IS_GP_PIN(pin->pin)) {
347 pfc_rcar_set_gpsr(pfc_base, pin->pin, true);
348 }
349
350 if ((pin->flags & RCAR_PIN_FLAGS_PULL_SET) != 0U) {
351 ret = pfc_rcar_set_bias(pfc_base, pin->pin, pin->flags);
352 if (ret < 0) {
353 return ret;
354 }
355 }
356 }
357
358 if (pin->drive_strength != 0U) {
359 ret = pfc_rcar_set_drive_strength(pfc_base, pin->pin,
360 pin->drive_strength);
361 }
362
363 return ret;
364 }
365
pinctrl_configure_pins(const pinctrl_soc_pin_t * pins,uint8_t pin_cnt,uintptr_t reg)366 int pinctrl_configure_pins(const pinctrl_soc_pin_t *pins, uint8_t pin_cnt,
367 uintptr_t reg)
368 {
369 int ret = 0;
370
371 ARG_UNUSED(reg);
372 while (pin_cnt-- > 0U) {
373 ret = pinctrl_configure_pin(pins++);
374 if (ret < 0) {
375 break;
376 }
377 }
378
379 return ret;
380 }
381
382 #if defined(DEVICE_MMIO_IS_IN_RAM)
pfc_rcar_driver_init(void)383 __boot_func static int pfc_rcar_driver_init(void)
384 {
385 for (unsigned int i = 0; i < ARRAY_SIZE(reg_base); i++) {
386 device_map(reg_base + i, reg_base[i], reg_sizes[i], K_MEM_CACHE_NONE);
387 }
388 return 0;
389 }
390
391 SYS_INIT(pfc_rcar_driver_init, PRE_KERNEL_1, CONFIG_KERNEL_INIT_PRIORITY_DEFAULT);
392 #endif
393