blob: 79d44bca039e1c65ecd667908463f37d12cf2a16 [file] [log] [blame]
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +05301// SPDX-License-Identifier: GPL-2.0
2/*
3 * Intel Thunder Bay SOC pinctrl/GPIO driver
4 *
5 * Copyright (C) 2021 Intel Corporation
6 */
7
8#include <linux/device.h>
9#include <linux/err.h>
10#include <linux/gpio/driver.h>
11#include <linux/init.h>
12#include <linux/interrupt.h>
13#include <linux/io.h>
14#include <linux/irq.h>
15#include <linux/module.h>
16#include <linux/of.h>
17#include <linux/of_irq.h>
18
19#include <linux/pinctrl/pinconf.h>
20#include <linux/pinctrl/pinconf-generic.h>
21#include <linux/pinctrl/pinctrl.h>
22#include <linux/pinctrl/pinmux.h>
23
24#include <linux/platform_device.h>
25#include <linux/slab.h>
26#include <linux/spinlock.h>
27
28#include "core.h"
29#include "pinconf.h"
30#include "pinctrl-utils.h"
31#include "pinmux.h"
32
33/* Bit 0:2 and 4:6 should be used for mode selection */
34#define THB_GPIO_PINMUX_MODE_0 0x00
35#define THB_GPIO_PINMUX_MODE_1 0x11
36#define THB_GPIO_PINMUX_MODE_2 0x22
37#define THB_GPIO_PINMUX_MODE_3 0x33
38#define THB_GPIO_PINMUX_MODE_4 0x44
39
40#define THB_GPIO_PORT_SELECT_MASK BIT(8)
41#define THB_GPIO_PAD_DIRECTION_MASK BIT(10)
42#define THB_GPIO_SPU_MASK BIT(11)
43#define THB_GPIO_PULL_ENABLE_MASK BIT(12)
44#define THB_GPIO_PULL_UP_MASK BIT(13)
45#define THB_GPIO_PULL_DOWN_MASK BIT(14)
46#define THB_GPIO_ENAQ_MASK BIT(15)
47/* bit 16-19: Drive Strength for the Pad */
48#define THB_GPIO_DRIVE_STRENGTH_MASK (0xF0000)
49#define THB_GPIO_SLEW_RATE_MASK BIT(20)
50#define THB_GPIO_SCHMITT_TRIGGER_MASK BIT(21)
51
52#define THB_GPIO_REG_OFFSET(pin_num) ((pin_num) * (0x4))
53#define THB_MAX_MODE_SUPPORTED (5u)
54#define THB_MAX_NPINS_SUPPORTED (67u)
55
56/* store Pin status */
57static u32 thb_pinx_status[THB_MAX_NPINS_SUPPORTED];
58
59struct thunderbay_mux_desc {
60 u8 mode;
61 const char *name;
62};
63
64#define THUNDERBAY_PIN_DESC(pin_number, pin_name, ...) { \
65 .number = pin_number, \
66 .name = pin_name, \
67 .drv_data = &(struct thunderbay_mux_desc[]) { \
68 __VA_ARGS__, { } }, \
69}
70
71#define THUNDERBAY_MUX(pin_mode, pin_function) { \
72 .mode = pin_mode, \
73 .name = pin_function, \
74}
75
76struct thunderbay_pin_soc {
77 const struct pinctrl_pin_desc *pins;
78 unsigned int npins;
79};
80
81/**
82 * struct thunderbay_pinctrl - Intel Thunderbay pinctrl structure
83 * @pctrl: Pointer to the pin controller device
84 * @base0: First register base address
85 * @dev: Pointer to the device structure
86 * @chip: GPIO chip used by this pin controller
87 * @soc: Pin control configuration data based on SoC
88 * @ngroups: Number of pin groups available
89 * @nfuncs: Number of pin functions available
90 */
91struct thunderbay_pinctrl {
92 struct pinctrl_dev *pctrl;
93 void __iomem *base0;
94 struct device *dev;
95 struct gpio_chip chip;
96 const struct thunderbay_pin_soc *soc;
97 unsigned int ngroups;
98 unsigned int nfuncs;
99};
100
101static const struct pinctrl_pin_desc thunderbay_pins[] = {
102 THUNDERBAY_PIN_DESC(0, "GPIO0",
103 THUNDERBAY_MUX(0X0, "I2C0_M0"),
104 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
105 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
106 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
107 THUNDERBAY_MUX(0X4, "GPIO_M4")),
108 THUNDERBAY_PIN_DESC(1, "GPIO1",
109 THUNDERBAY_MUX(0X0, "I2C0_M0"),
110 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
111 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
112 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
113 THUNDERBAY_MUX(0X4, "GPIO_M4")),
114 THUNDERBAY_PIN_DESC(2, "GPIO2",
115 THUNDERBAY_MUX(0X0, "I2C1_M0"),
116 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
117 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
118 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
119 THUNDERBAY_MUX(0X4, "GPIO_M4")),
120 THUNDERBAY_PIN_DESC(3, "GPIO3",
121 THUNDERBAY_MUX(0X0, "I2C1_M0"),
122 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
123 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
124 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
125 THUNDERBAY_MUX(0X4, "GPIO_M4")),
126 THUNDERBAY_PIN_DESC(4, "GPIO4",
127 THUNDERBAY_MUX(0X0, "I2C2_M0"),
128 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
129 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
130 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
131 THUNDERBAY_MUX(0X4, "GPIO_M4")),
132 THUNDERBAY_PIN_DESC(5, "GPIO5",
133 THUNDERBAY_MUX(0X0, "I2C2_M0"),
134 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
135 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
136 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
137 THUNDERBAY_MUX(0X4, "GPIO_M4")),
138 THUNDERBAY_PIN_DESC(6, "GPIO6",
139 THUNDERBAY_MUX(0X0, "I2C3_M0"),
140 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
141 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
142 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
143 THUNDERBAY_MUX(0X4, "GPIO_M4")),
144 THUNDERBAY_PIN_DESC(7, "GPIO7",
145 THUNDERBAY_MUX(0X0, "I2C3_M0"),
146 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
147 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
148 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
149 THUNDERBAY_MUX(0X4, "GPIO_M4")),
150 THUNDERBAY_PIN_DESC(8, "GPIO8",
151 THUNDERBAY_MUX(0X0, "I2C4_M0"),
152 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
153 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
154 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
155 THUNDERBAY_MUX(0X4, "GPIO_M4")),
156 THUNDERBAY_PIN_DESC(9, "GPIO9",
157 THUNDERBAY_MUX(0X0, "I2C4_M0"),
158 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
159 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
160 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
161 THUNDERBAY_MUX(0X4, "GPIO_M4")),
162 THUNDERBAY_PIN_DESC(10, "GPIO10",
163 THUNDERBAY_MUX(0X0, "UART0_M0"),
164 THUNDERBAY_MUX(0X1, "RT0_DSU_M1"),
165 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
166 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
167 THUNDERBAY_MUX(0X4, "GPIO_M4")),
168 THUNDERBAY_PIN_DESC(11, "GPIO11",
169 THUNDERBAY_MUX(0X0, "UART0_M0"),
170 THUNDERBAY_MUX(0X1, "RT0_DSU_M1"),
171 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
172 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
173 THUNDERBAY_MUX(0X4, "GPIO_M4")),
174 THUNDERBAY_PIN_DESC(12, "GPIO12",
175 THUNDERBAY_MUX(0X0, "UART0_M0"),
176 THUNDERBAY_MUX(0X1, "RT1_DSU_M1"),
177 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
178 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
179 THUNDERBAY_MUX(0X4, "GPIO_M4")),
180 THUNDERBAY_PIN_DESC(13, "GPIO13",
181 THUNDERBAY_MUX(0X0, "UART0_M0"),
182 THUNDERBAY_MUX(0X1, "RT1_DSU_M1"),
183 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
184 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
185 THUNDERBAY_MUX(0X4, "GPIO_M4")),
186 THUNDERBAY_PIN_DESC(14, "GPIO14",
187 THUNDERBAY_MUX(0X0, "UART1_M0"),
188 THUNDERBAY_MUX(0X1, "RT2_DSU_M1"),
189 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
190 THUNDERBAY_MUX(0X3, "TRIGGER_M3"),
191 THUNDERBAY_MUX(0X4, "GPIO_M4")),
192 THUNDERBAY_PIN_DESC(15, "GPIO15",
193 THUNDERBAY_MUX(0X0, "UART1_M0"),
194 THUNDERBAY_MUX(0X1, "RT2_DSU_M1"),
195 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
196 THUNDERBAY_MUX(0X3, "TRIGGER_M3"),
197 THUNDERBAY_MUX(0X4, "GPIO_M4")),
198 THUNDERBAY_PIN_DESC(16, "GPIO16",
199 THUNDERBAY_MUX(0X0, "UART1_M0"),
200 THUNDERBAY_MUX(0X1, "RT3_DSU_M1"),
201 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
202 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
203 THUNDERBAY_MUX(0X4, "GPIO_M4")),
204 THUNDERBAY_PIN_DESC(17, "GPIO17",
205 THUNDERBAY_MUX(0X0, "UART1_M0"),
206 THUNDERBAY_MUX(0X1, "RT3_DSU_M1"),
207 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
208 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
209 THUNDERBAY_MUX(0X4, "GPIO_M4")),
210 THUNDERBAY_PIN_DESC(18, "GPIO18",
211 THUNDERBAY_MUX(0X0, "SPI0_M0"),
212 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
213 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
214 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
215 THUNDERBAY_MUX(0X4, "GPIO_M4")),
216 THUNDERBAY_PIN_DESC(19, "GPIO19",
217 THUNDERBAY_MUX(0X0, "SPI0_M0"),
218 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
219 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
220 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
221 THUNDERBAY_MUX(0X4, "GPIO_M4")),
222 THUNDERBAY_PIN_DESC(20, "GPIO20",
223 THUNDERBAY_MUX(0X0, "SPI0_M0"),
224 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
225 THUNDERBAY_MUX(0X2, "TPIU_TRACE_M2"),
226 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
227 THUNDERBAY_MUX(0X4, "GPIO_M4")),
228 THUNDERBAY_PIN_DESC(21, "GPIO21",
229 THUNDERBAY_MUX(0X0, "SPI0_M0"),
230 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
231 THUNDERBAY_MUX(0X2, "TPIU_TRACE_M2"),
232 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
233 THUNDERBAY_MUX(0X4, "GPIO_M4")),
234 THUNDERBAY_PIN_DESC(22, "GPIO22",
235 THUNDERBAY_MUX(0X0, "SPI1_M0"),
236 THUNDERBAY_MUX(0X1, "EMPTY_M0"),
237 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
238 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
239 THUNDERBAY_MUX(0X4, "GPIO_M4")),
240 THUNDERBAY_PIN_DESC(23, "GPIO23",
241 THUNDERBAY_MUX(0X0, "SPI1_M0"),
242 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
243 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
244 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
245 THUNDERBAY_MUX(0X4, "GPIO_M4")),
246 THUNDERBAY_PIN_DESC(24, "GPIO24",
247 THUNDERBAY_MUX(0X0, "SPI1_M0"),
248 THUNDERBAY_MUX(0X1, "TPIU_TRACE_M1"),
249 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
250 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
251 THUNDERBAY_MUX(0X4, "GPIO_M4")),
252 THUNDERBAY_PIN_DESC(25, "GPIO25",
253 THUNDERBAY_MUX(0X0, "SPI1_M0"),
254 THUNDERBAY_MUX(0X1, "TPIU_TRACE_M1"),
255 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
256 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
257 THUNDERBAY_MUX(0X4, "GPIO_M4")),
258 THUNDERBAY_PIN_DESC(26, "GPIO26",
259 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
260 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
261 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
262 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
263 THUNDERBAY_MUX(0X4, "GPIO_M4")),
264 THUNDERBAY_PIN_DESC(27, "GPIO27",
265 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
266 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
267 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
268 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
269 THUNDERBAY_MUX(0X4, "GPIO_M4")),
270 THUNDERBAY_PIN_DESC(28, "GPIO28",
271 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
272 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
273 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
274 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
275 THUNDERBAY_MUX(0X4, "GPIO_M4")),
276 THUNDERBAY_PIN_DESC(29, "GPIO29",
277 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
278 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
279 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
280 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
281 THUNDERBAY_MUX(0X4, "GPIO_M4")),
282 THUNDERBAY_PIN_DESC(30, "GPIO30",
283 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
284 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
285 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
286 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
287 THUNDERBAY_MUX(0X4, "GPIO_M4")),
288 THUNDERBAY_PIN_DESC(31, "GPIO31",
289 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
290 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
291 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
292 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
293 THUNDERBAY_MUX(0X4, "GPIO_M4")),
294 THUNDERBAY_PIN_DESC(32, "GPIO32",
295 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
296 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
297 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
298 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
299 THUNDERBAY_MUX(0X4, "GPIO_M4")),
300 THUNDERBAY_PIN_DESC(33, "GPIO33",
301 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
302 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
303 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
304 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
305 THUNDERBAY_MUX(0X4, "GPIO_M4")),
306 THUNDERBAY_PIN_DESC(34, "GPIO34",
307 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
308 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
309 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
310 THUNDERBAY_MUX(0X3, "DIG_VIEW_0"),
311 THUNDERBAY_MUX(0X4, "GPIO_M4")),
312 THUNDERBAY_PIN_DESC(35, "GPIO35",
313 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
314 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
315 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
316 THUNDERBAY_MUX(0X3, "DIG_VIEW_1"),
317 THUNDERBAY_MUX(0X4, "GPIO_M4")),
318 THUNDERBAY_PIN_DESC(36, "GPIO36",
319 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
320 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
321 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
322 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_0"),
323 THUNDERBAY_MUX(0X4, "GPIO_M4")),
324 THUNDERBAY_PIN_DESC(37, "GPIO37",
325 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
326 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
327 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
328 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_1"),
329 THUNDERBAY_MUX(0X4, "GPIO_M4")),
330 THUNDERBAY_PIN_DESC(38, "GPIO38",
331 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
332 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
333 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
334 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_2"),
335 THUNDERBAY_MUX(0X4, "GPIO_M4")),
336 THUNDERBAY_PIN_DESC(39, "GPIO39",
337 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
338 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
339 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
340 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_3"),
341 THUNDERBAY_MUX(0X4, "GPIO_M4")),
342 THUNDERBAY_PIN_DESC(40, "GPIO40",
343 THUNDERBAY_MUX(0X0, "ETHER0_M0"),
344 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
345 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
346 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
347 THUNDERBAY_MUX(0X4, "GPIO_M4")),
348 THUNDERBAY_PIN_DESC(41, "GPIO41",
349 THUNDERBAY_MUX(0X0, "POWER_INTERRUPT_MAX_PLATFORM_POWER_M0"),
350 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
351 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
352 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
353 THUNDERBAY_MUX(0X4, "GPIO_M4")),
354 THUNDERBAY_PIN_DESC(42, "GPIO42",
355 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
356 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
357 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
358 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
359 THUNDERBAY_MUX(0X4, "GPIO_M4")),
360 THUNDERBAY_PIN_DESC(43, "GPIO43",
361 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
362 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
363 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
364 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
365 THUNDERBAY_MUX(0X4, "GPIO_M4")),
366 THUNDERBAY_PIN_DESC(44, "GPIO44",
367 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
368 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
369 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
370 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
371 THUNDERBAY_MUX(0X4, "GPIO_M4")),
372 THUNDERBAY_PIN_DESC(45, "GPIO45",
373 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
374 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
375 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
376 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
377 THUNDERBAY_MUX(0X4, "GPIO_M4")),
378 THUNDERBAY_PIN_DESC(46, "GPIO46",
379 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
380 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
381 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
382 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
383 THUNDERBAY_MUX(0X4, "GPIO_M4")),
384 THUNDERBAY_PIN_DESC(47, "GPIO47",
385 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
386 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
387 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
388 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
389 THUNDERBAY_MUX(0X4, "GPIO_M4")),
390 THUNDERBAY_PIN_DESC(48, "GPIO48",
391 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
392 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
393 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
394 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
395 THUNDERBAY_MUX(0X4, "GPIO_M4")),
396 THUNDERBAY_PIN_DESC(49, "GPIO49",
397 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
398 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
399 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
400 THUNDERBAY_MUX(0X3, "DEBUG_M3"),
401 THUNDERBAY_MUX(0X4, "GPIO_M4")),
402 THUNDERBAY_PIN_DESC(50, "GPIO50",
403 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
404 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
405 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
406 THUNDERBAY_MUX(0X3, "DIG_VIEW_0"),
407 THUNDERBAY_MUX(0X4, "GPIO_M4")),
408 THUNDERBAY_PIN_DESC(51, "GPIO51",
409 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
410 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
411 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
412 THUNDERBAY_MUX(0X3, "DIG_VIEW_1"),
413 THUNDERBAY_MUX(0X4, "GPIO_M4")),
414 THUNDERBAY_PIN_DESC(52, "GPIO52",
415 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
416 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
417 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
418 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_0"),
419 THUNDERBAY_MUX(0X4, "GPIO_M4")),
420 THUNDERBAY_PIN_DESC(53, "GPIO53",
421 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
422 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
423 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
424 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_1"),
425 THUNDERBAY_MUX(0X4, "GPIO_M4")),
426 THUNDERBAY_PIN_DESC(54, "GPIO54",
427 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
428 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
429 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
430 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_2"),
431 THUNDERBAY_MUX(0X4, "GPIO_M4")),
432 THUNDERBAY_PIN_DESC(55, "GPIO55",
433 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
434 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
435 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
436 THUNDERBAY_MUX(0X3, "CPR_IO_OUT_CLK_3"),
437 THUNDERBAY_MUX(0X4, "GPIO_M4")),
438 THUNDERBAY_PIN_DESC(56, "GPIO56",
439 THUNDERBAY_MUX(0X0, "ETHER1_M0"),
440 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
441 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
442 THUNDERBAY_MUX(0X3, "POWER_INTERRUPT_ICCMAX_VDDD_M3"),
443 THUNDERBAY_MUX(0X4, "GPIO_M4")),
444 THUNDERBAY_PIN_DESC(57, "GPIO57",
445 THUNDERBAY_MUX(0X0, "POWER_INTERRUPT_ICCMAX_VPU_M0"),
446 THUNDERBAY_MUX(0X1, "TPIU_DATA_M1"),
447 THUNDERBAY_MUX(0X2, "TPIU_DATA_M2"),
448 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
449 THUNDERBAY_MUX(0X4, "GPIO_M4")),
450 THUNDERBAY_PIN_DESC(58, "GPIO58",
451 THUNDERBAY_MUX(0X0, "THERMTRIP_M0"),
452 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
453 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
454 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
455 THUNDERBAY_MUX(0X4, "GPIO_M4")),
456 THUNDERBAY_PIN_DESC(59, "GPIO59",
457 THUNDERBAY_MUX(0X0, "THERMTRIP_M0"),
458 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
459 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
460 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
461 THUNDERBAY_MUX(0X4, "GPIO_M4")),
462 THUNDERBAY_PIN_DESC(60, "GPIO60",
463 THUNDERBAY_MUX(0X0, "SMBUS_M0"),
464 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
465 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
466 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
467 THUNDERBAY_MUX(0X4, "GPIO_M4")),
468 THUNDERBAY_PIN_DESC(61, "GPIO61",
469 THUNDERBAY_MUX(0X0, "SMBUS_M0"),
470 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
471 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
472 THUNDERBAY_MUX(0X3, "POWER_INTERRUPT_ICCMAX_VDDD_M3"),
473 THUNDERBAY_MUX(0X4, "GPIO_M4")),
474 THUNDERBAY_PIN_DESC(62, "GPIO62",
475 THUNDERBAY_MUX(0X0, "PLATFORM_RESET_M0"),
476 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
477 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
478 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
479 THUNDERBAY_MUX(0X4, "GPIO_M4")),
480 THUNDERBAY_PIN_DESC(63, "GPIO63",
481 THUNDERBAY_MUX(0X0, "PLATFORM_RESET_M0"),
482 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
483 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
484 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
485 THUNDERBAY_MUX(0X4, "GPIO_M4")),
486 THUNDERBAY_PIN_DESC(64, "GPIO64",
487 THUNDERBAY_MUX(0X0, "PLATFORM_SHUTDOWN_M0"),
488 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
489 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
490 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
491 THUNDERBAY_MUX(0X4, "GPIO_M4")),
492 THUNDERBAY_PIN_DESC(65, "GPIO65",
493 THUNDERBAY_MUX(0X0, "PLATFORM_SHUTDOWN_M0"),
494 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
495 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
496 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
497 THUNDERBAY_MUX(0X4, "GPIO_M4")),
498 THUNDERBAY_PIN_DESC(66, "GPIO66",
499 THUNDERBAY_MUX(0X0, "POWER_INTERRUPT_ICCMAX_MEDIA_M0"),
500 THUNDERBAY_MUX(0X1, "EMPTY_M1"),
501 THUNDERBAY_MUX(0X2, "EMPTY_M2"),
502 THUNDERBAY_MUX(0X3, "EMPTY_M3"),
503 THUNDERBAY_MUX(0X4, "GPIO_M4")),
504};
505
506static const struct thunderbay_pin_soc thunderbay_data = {
507 .pins = thunderbay_pins,
508 .npins = ARRAY_SIZE(thunderbay_pins),
509};
510
511static u32 thb_gpio_read_reg(struct gpio_chip *chip, unsigned int pinnr)
512{
513 struct thunderbay_pinctrl *tpc = gpiochip_get_data(chip);
514
515 return readl(tpc->base0 + THB_GPIO_REG_OFFSET(pinnr));
516}
517
518static u32 thb_gpio_write_reg(struct gpio_chip *chip, unsigned int pinnr, u32 value)
519{
520 struct thunderbay_pinctrl *tpc = gpiochip_get_data(chip);
521
522 writel(value, (tpc->base0 + THB_GPIO_REG_OFFSET(pinnr)));
523 return 0;
524}
525
526static int thb_read_gpio_data(struct gpio_chip *chip, unsigned int offset, unsigned int pad_dir)
527{
528 int data_offset;
529 u32 data_reg;
530
531 /* as per GPIO Spec = pad_dir 0:input, 1:output */
532 data_offset = 0x2000u + (offset / 32);
533 if (!pad_dir)
534 data_offset += 4;
535 data_reg = thb_gpio_read_reg(chip, data_offset);
536
537 return data_reg & BIT(offset % 32);
538}
539
540static int thb_write_gpio_data(struct gpio_chip *chip, unsigned int offset, unsigned int value)
541{
542 int data_offset;
543 u32 data_reg;
544
545 data_offset = 0x2000u + (offset / 32);
546
547 data_reg = thb_gpio_read_reg(chip, data_offset);
548
549 if (value > 0)
550 data_reg |= BIT(offset % 32);
551 else
552 data_reg &= ~BIT(offset % 32);
553
554 return thb_gpio_write_reg(chip, data_offset, data_reg);
555}
556
557static int thunderbay_gpio_get_direction(struct gpio_chip *chip, unsigned int offset)
558{
559 u32 reg = thb_gpio_read_reg(chip, offset);
560
561 /* Return direction only if configured as GPIO else negative error */
562 if (reg & THB_GPIO_PORT_SELECT_MASK)
563 return !(reg & THB_GPIO_PAD_DIRECTION_MASK);
564 return -EINVAL;
565}
566
567static int thunderbay_gpio_set_direction_input(struct gpio_chip *chip, unsigned int offset)
568{
569 u32 reg = thb_gpio_read_reg(chip, offset);
570
571 /* set pin as input only if it is GPIO else error */
572 if (reg & THB_GPIO_PORT_SELECT_MASK) {
573 reg &= (~THB_GPIO_PAD_DIRECTION_MASK);
574 thb_gpio_write_reg(chip, offset, reg);
575 return 0;
576 }
577 return -EINVAL;
578}
579
580static void thunderbay_gpio_set_value(struct gpio_chip *chip, unsigned int offset, int value)
581{
582 u32 reg = thb_gpio_read_reg(chip, offset);
583
584 /* update pin value only if it is GPIO-output else error */
585 if ((reg & THB_GPIO_PORT_SELECT_MASK) && (reg & THB_GPIO_PAD_DIRECTION_MASK))
586 thb_write_gpio_data(chip, offset, value);
587}
588
589static int thunderbay_gpio_set_direction_output(struct gpio_chip *chip,
590 unsigned int offset, int value)
591{
592 u32 reg = thb_gpio_read_reg(chip, offset);
593
594 /* set pin as output only if it is GPIO else error */
595 if (reg & THB_GPIO_PORT_SELECT_MASK) {
596 reg |= THB_GPIO_PAD_DIRECTION_MASK;
597 thb_gpio_write_reg(chip, offset, reg);
598 thunderbay_gpio_set_value(chip, offset, value);
599 return 0;
600 }
601 return -EINVAL;
602}
603
604static int thunderbay_gpio_get_value(struct gpio_chip *chip, unsigned int offset)
605{
606 u32 reg = thb_gpio_read_reg(chip, offset);
607 int gpio_dir = 0;
608
609 /* Read pin value only if it is GPIO else error */
610 if (reg & THB_GPIO_PORT_SELECT_MASK) {
611 /* 0=in, 1=out */
612 gpio_dir = (reg & THB_GPIO_PAD_DIRECTION_MASK) > 0;
613
614 /* Returns negative value when pin is configured as PORT */
615 return thb_read_gpio_data(chip, offset, gpio_dir);
616 }
617 return -EINVAL;
618}
619
620static int thunderbay_gpiochip_probe(struct thunderbay_pinctrl *tpc)
621{
622 struct gpio_chip *chip = &tpc->chip;
623 int ret;
624
625 chip->label = dev_name(tpc->dev);
626 chip->parent = tpc->dev;
627 chip->request = gpiochip_generic_request;
628 chip->free = gpiochip_generic_free;
629 chip->get_direction = thunderbay_gpio_get_direction;
630 chip->direction_input = thunderbay_gpio_set_direction_input;
631 chip->direction_output = thunderbay_gpio_set_direction_output;
632 chip->get = thunderbay_gpio_get_value;
633 chip->set = thunderbay_gpio_set_value;
634 chip->set_config = gpiochip_generic_config;
635 /* identifies the first GPIO number handled by this chip; or,
636 * if negative during registration, requests dynamic ID allocation.
637 * Please pass -1 as base to let gpiolib select the chip base in all possible cases.
638 * We want to get rid of the static GPIO number space in the long run.
639 */
640 chip->base = -1;
641 /* Number of GPIOs handled by this controller; the last GPIO handled is (base + ngpio - 1)*/
642 chip->ngpio = THB_MAX_NPINS_SUPPORTED;
643
644 /* Register/add Thunder Bay GPIO chip with Linux framework */
645 ret = gpiochip_add_data(chip, tpc);
646 if (ret)
647 dev_err(tpc->dev, "Failed to add gpiochip\n");
648 return ret;
649}
650
651static int thunderbay_request_gpio(struct pinctrl_dev *pctldev,
652 struct pinctrl_gpio_range *range,
653 unsigned int pin)
654{
655 struct thunderbay_pinctrl *tpc = pinctrl_dev_get_drvdata(pctldev);
656 struct gpio_chip *chip = &tpc->chip;
657 u32 reg = 0;
658
659 if (thb_pinx_status[pin] == 0u) {
660 reg = thb_gpio_read_reg(chip, pin);
661 /* Updates PIN configuration as GPIO and sets GPIO to MODE-4*/
662 reg |= (THB_GPIO_PORT_SELECT_MASK | THB_GPIO_PINMUX_MODE_4);
663 thb_gpio_write_reg(chip, pin, reg);
664
665 /* update pin status as busy */
666 thb_pinx_status[pin] = 1u;
667
668 return 0;
669 }
670 return -EINVAL;
671}
672
673static void thunderbay_free_gpio(struct pinctrl_dev *pctldev,
674 struct pinctrl_gpio_range *range,
675 unsigned int pin)
676{
677 struct thunderbay_pinctrl *tpc = pinctrl_dev_get_drvdata(pctldev);
678 struct gpio_chip *chip = &tpc->chip;
679 u32 reg = 0;
680
681 if (thb_pinx_status[pin] == 1u) {
682 reg = thb_gpio_read_reg(chip, pin);
683
684 /* Updates PIN configuration from GPIO to PORT */
685 reg &= (~THB_GPIO_PORT_SELECT_MASK);
686
687 /* Change Port/gpio mode to default mode-0 */
688 reg &= (~THB_GPIO_PINMUX_MODE_4);
689
690 thb_gpio_write_reg(chip, pin, reg);
691
692 /* update pin status as free */
693 thb_pinx_status[pin] = 0u;
694 }
695}
696
697static int thb_pinctrl_set_mux(struct pinctrl_dev *pctldev,
698 unsigned int func_select, unsigned int group_select)
699{
700 struct thunderbay_pinctrl *tpc = pinctrl_dev_get_drvdata(pctldev);
701 struct gpio_chip *chip = &tpc->chip;
702 struct function_desc *function;
703 unsigned int i, pin_mode;
704 struct group_desc *group;
705 int ret = -EINVAL;
706 u32 reg = 0u;
707
708 group = pinctrl_generic_get_group(pctldev, group_select);
709 if (!group)
710 return -EINVAL;
711
712 function = pinmux_generic_get_function(pctldev, func_select);
713 if (!function)
714 return -EINVAL;
715
716 pin_mode = *(unsigned int *)(function->data);
717
718 /* Change modes for pins in the selected group */
719 for (i = 0; i < group->num_pins; i++) {
720 reg = thb_gpio_read_reg(chip, group->pins[i]);
721
722 switch (pin_mode) {
723 case 0u:
724 reg |= THB_GPIO_PINMUX_MODE_0;
725 break;
726 case 1u:
727 reg |= THB_GPIO_PINMUX_MODE_1;
728 break;
729 case 2u:
730 reg |= THB_GPIO_PINMUX_MODE_2;
731 break;
732 case 3u:
733 reg |= THB_GPIO_PINMUX_MODE_3;
734 break;
735 case 4u:
736 reg |= THB_GPIO_PINMUX_MODE_4;
737 break;
738 default:
739 return -EINVAL;
740 }
741
742 ret = thb_gpio_write_reg(chip, group->pins[i], reg);
743 if (~ret) {
744 /* update pin status as busy */
745 thb_pinx_status[group->pins[i]] = 1u;
746 }
747 }
748 return ret;
749}
750
751static int thunderbay_build_groups(struct thunderbay_pinctrl *tpc)
752{
753 struct group_desc *thunderbay_groups;
754 int i;
755
756 tpc->ngroups = tpc->soc->npins;
757 thunderbay_groups = devm_kcalloc(tpc->dev, tpc->ngroups,
758 sizeof(*thunderbay_groups), GFP_KERNEL);
759 if (!thunderbay_groups)
760 return -ENOMEM;
761
762 for (i = 0; i < tpc->ngroups; i++) {
763 struct group_desc *group = thunderbay_groups + i;
764 const struct pinctrl_pin_desc *pin_info = thunderbay_pins + i;
765
766 group->name = pin_info->name;
767 group->pins = (int *)&pin_info->number;
768 pinctrl_generic_add_group(tpc->pctrl, group->name,
769 group->pins, 1, NULL);
770 }
771 return 0;
772}
773
774static int thunderbay_add_functions(struct thunderbay_pinctrl *tpc, struct function_desc *funcs)
775{
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530776 int i;
777
778 /* Assign the groups for each function */
Rafał Miłecki25d2e412022-01-11 18:29:19 +0100779 for (i = 0; i < tpc->nfuncs; i++) {
780 struct function_desc *func = &funcs[i];
781 const char **group_names;
782 unsigned int grp_idx = 0;
783 int j;
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530784
Rafał Miłecki25d2e412022-01-11 18:29:19 +0100785 group_names = devm_kcalloc(tpc->dev, func->num_group_names,
786 sizeof(*group_names), GFP_KERNEL);
787 if (!group_names)
788 return -ENOMEM;
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530789
Rafał Miłecki25d2e412022-01-11 18:29:19 +0100790 for (j = 0; j < tpc->soc->npins; j++) {
791 const struct pinctrl_pin_desc *pin_info = &thunderbay_pins[j];
792 struct thunderbay_mux_desc *pin_mux;
793
794 for (pin_mux = pin_info->drv_data; pin_mux->name; pin_mux++) {
795 if (!strcmp(pin_mux->name, func->name))
796 group_names[grp_idx++] = pin_info->name;
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530797 }
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530798 }
Rafał Miłecki25d2e412022-01-11 18:29:19 +0100799
800 func->group_names = group_names;
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530801 }
802
803 /* Add all functions */
804 for (i = 0; i < tpc->nfuncs; i++) {
805 pinmux_generic_add_function(tpc->pctrl,
Rafał Miłecki25d2e412022-01-11 18:29:19 +0100806 funcs[i].name,
807 funcs[i].group_names,
808 funcs[i].num_group_names,
809 funcs[i].data);
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530810 }
Rafał Miłecki25d2e412022-01-11 18:29:19 +0100811 kfree(funcs);
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530812 return 0;
813}
814
815static int thunderbay_build_functions(struct thunderbay_pinctrl *tpc)
816{
817 struct function_desc *thunderbay_funcs;
818 void *ptr;
819 int pin;
820
Rafał Miłecki30cc5382022-01-11 18:29:18 +0100821 /*
822 * Allocate maximum possible number of functions. Assume every pin
823 * being part of 8 (hw maximum) globally unique muxes.
824 */
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530825 tpc->nfuncs = 0;
826 thunderbay_funcs = kcalloc(tpc->soc->npins * 8,
827 sizeof(*thunderbay_funcs), GFP_KERNEL);
828 if (!thunderbay_funcs)
829 return -ENOMEM;
830
Rafał Miłecki30cc5382022-01-11 18:29:18 +0100831 /* Setup 1 function for each unique mux */
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530832 for (pin = 0; pin < tpc->soc->npins; pin++) {
833 const struct pinctrl_pin_desc *pin_info = thunderbay_pins + pin;
Rafał Miłecki30cc5382022-01-11 18:29:18 +0100834 struct thunderbay_mux_desc *pin_mux;
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530835
Rafał Miłecki30cc5382022-01-11 18:29:18 +0100836 for (pin_mux = pin_info->drv_data; pin_mux->name; pin_mux++) {
837 struct function_desc *func;
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530838
Rafał Miłecki30cc5382022-01-11 18:29:18 +0100839 /* Check if we already have function for this mux */
840 for (func = thunderbay_funcs; func->name; func++) {
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530841 if (!strcmp(pin_mux->name, func->name)) {
842 func->num_group_names++;
843 break;
844 }
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530845 }
846
847 if (!func->name) {
848 func->name = pin_mux->name;
849 func->num_group_names = 1;
850 func->data = (int *)&pin_mux->mode;
851 tpc->nfuncs++;
852 }
Lakshmi Sowjanya D12422af2021-12-01 12:56:26 +0530853 }
854 }
855
856 /* Reallocate memory based on actual number of functions */
857 ptr = krealloc(thunderbay_funcs,
858 tpc->nfuncs * sizeof(*thunderbay_funcs), GFP_KERNEL);
859 if (!ptr)
860 return -ENOMEM;
861
862 thunderbay_funcs = ptr;
863 return thunderbay_add_functions(tpc, thunderbay_funcs);
864}
865
866static int thunderbay_pinconf_set_tristate(struct thunderbay_pinctrl *tpc,
867 unsigned int pin, u32 config)
868{
869 struct gpio_chip *chip = &tpc->chip;
870 u32 reg;
871
872 reg = thb_gpio_read_reg(chip, pin);
873 if (config > 0)
874 reg |= THB_GPIO_ENAQ_MASK;
875 else
876 reg &= ~THB_GPIO_ENAQ_MASK;
877
878 return thb_gpio_write_reg(chip, pin, reg);
879}
880
881static int thunderbay_pinconf_get_tristate(struct thunderbay_pinctrl *tpc,
882 unsigned int pin, u32 *config)
883{
884 struct gpio_chip *chip = &tpc->chip;
885 u32 reg;
886
887 reg = thb_gpio_read_reg(chip, pin);
888 *config = (reg & THB_GPIO_ENAQ_MASK) > 0;
889
890 return 0;
891}
892
893static int thunderbay_pinconf_set_pulldown(struct thunderbay_pinctrl *tpc,
894 unsigned int pin, u32 config)
895{
896 struct gpio_chip *chip = &tpc->chip;
897 u32 reg;
898
899 reg = thb_gpio_read_reg(chip, pin);
900 if (config > 0)
901 reg |= THB_GPIO_PULL_DOWN_MASK;
902 else
903 reg &= ~THB_GPIO_PULL_DOWN_MASK;
904
905 return thb_gpio_write_reg(chip, pin, reg);
906}
907
908static int thunderbay_pinconf_get_pulldown(struct thunderbay_pinctrl *tpc,
909 unsigned int pin, u32 *config)
910{
911 struct gpio_chip *chip = &tpc->chip;
912 u32 reg = 0;
913
914 reg = thb_gpio_read_reg(chip, pin);
915 *config = ((reg & THB_GPIO_PULL_DOWN_MASK) > 0) ? 1 : 0;
916
917 return 0;
918}
919
920static int thunderbay_pinconf_set_pullup(struct thunderbay_pinctrl *tpc,
921 unsigned int pin, u32 config)
922{
923 struct gpio_chip *chip = &tpc->chip;
924 u32 reg;
925
926 reg = thb_gpio_read_reg(chip, pin);
927 if (config > 0)
928 reg &= ~THB_GPIO_PULL_UP_MASK;
929 else
930 reg |= THB_GPIO_PULL_UP_MASK;
931
932 return thb_gpio_write_reg(chip, pin, reg);
933}
934
935static int thunderbay_pinconf_get_pullup(struct thunderbay_pinctrl *tpc,
936 unsigned int pin, u32 *config)
937{
938 struct gpio_chip *chip = &tpc->chip;
939 u32 reg;
940
941 reg = thb_gpio_read_reg(chip, pin);
942 *config = ((reg & THB_GPIO_PULL_UP_MASK) == 0) ? 1 : 0;
943
944 return 0;
945}
946
947static int thunderbay_pinconf_set_opendrain(struct thunderbay_pinctrl *tpc,
948 unsigned int pin, u32 config)
949{
950 struct gpio_chip *chip = &tpc->chip;
951 u32 reg;
952
953 reg = thb_gpio_read_reg(chip, pin);
954 if (config > 0)
955 reg &= ~THB_GPIO_PULL_ENABLE_MASK;
956 else
957 reg |= THB_GPIO_PULL_ENABLE_MASK;
958
959 return thb_gpio_write_reg(chip, pin, reg);
960}
961
962static int thunderbay_pinconf_get_opendrain(struct thunderbay_pinctrl *tpc,
963 unsigned int pin, u32 *config)
964{
965 struct gpio_chip *chip = &tpc->chip;
966 u32 reg;
967
968 reg = thb_gpio_read_reg(chip, pin);
969 *config = ((reg & THB_GPIO_PULL_ENABLE_MASK) == 0) ? 1 : 0;
970
971 return 0;
972}
973
974static int thunderbay_pinconf_set_pushpull(struct thunderbay_pinctrl *tpc,
975 unsigned int pin, u32 config)
976{
977 struct gpio_chip *chip = &tpc->chip;
978 u32 reg;
979
980 reg = thb_gpio_read_reg(chip, pin);
981 if (config > 0)
982 reg |= THB_GPIO_PULL_ENABLE_MASK;
983 else
984 reg &= ~THB_GPIO_PULL_ENABLE_MASK;
985
986 return thb_gpio_write_reg(chip, pin, reg);
987}
988
989static int thunderbay_pinconf_get_pushpull(struct thunderbay_pinctrl *tpc,
990 unsigned int pin, u32 *config)
991{
992 struct gpio_chip *chip = &tpc->chip;
993 u32 reg;
994
995 reg = thb_gpio_read_reg(chip, pin);
996 *config = ((reg & THB_GPIO_PULL_ENABLE_MASK) > 0) ? 1 : 0;
997
998 return 0;
999}
1000
1001static int thunderbay_pinconf_set_drivestrength(struct thunderbay_pinctrl *tpc,
1002 unsigned int pin, u32 config)
1003{
1004 struct gpio_chip *chip = &tpc->chip;
1005 u32 reg;
1006
1007 reg = thb_gpio_read_reg(chip, pin);
1008
1009 /* Drive Strength: 0x0 to 0xF */
1010 if (config <= 0xF) {
1011 reg = (reg | config);
1012 return thb_gpio_write_reg(chip, pin, reg);
1013 }
1014
1015 return -EINVAL;
1016}
1017
1018static int thunderbay_pinconf_get_drivestrength(struct thunderbay_pinctrl *tpc,
1019 unsigned int pin, u32 *config)
1020{
1021 struct gpio_chip *chip = &tpc->chip;
1022 u32 reg;
1023
1024 reg = thb_gpio_read_reg(chip, pin);
1025 reg = (reg & THB_GPIO_DRIVE_STRENGTH_MASK) >> 16;
1026 *config = (reg > 0) ? reg : 0;
1027
1028 return 0;
1029}
1030
1031static int thunderbay_pinconf_set_schmitt(struct thunderbay_pinctrl *tpc,
1032 unsigned int pin, u32 config)
1033{
1034 struct gpio_chip *chip = &tpc->chip;
1035 u32 reg;
1036
1037 reg = thb_gpio_read_reg(chip, pin);
1038 if (config > 0)
1039 reg |= THB_GPIO_SCHMITT_TRIGGER_MASK;
1040 else
1041 reg &= ~THB_GPIO_SCHMITT_TRIGGER_MASK;
1042
1043 return thb_gpio_write_reg(chip, pin, reg);
1044}
1045
1046static int thunderbay_pinconf_get_schmitt(struct thunderbay_pinctrl *tpc,
1047 unsigned int pin, u32 *config)
1048{
1049 struct gpio_chip *chip = &tpc->chip;
1050 u32 reg;
1051
1052 reg = thb_gpio_read_reg(chip, pin);
1053 *config = ((reg & THB_GPIO_SCHMITT_TRIGGER_MASK) > 0) ? 1 : 0;
1054
1055 return 0;
1056}
1057
1058static int thunderbay_pinconf_set_slew_rate(struct thunderbay_pinctrl *tpc,
1059 unsigned int pin, u32 config)
1060{
1061 struct gpio_chip *chip = &tpc->chip;
1062 u32 reg = 0;
1063
1064 reg = thb_gpio_read_reg(chip, pin);
1065 if (config > 0)
1066 reg |= THB_GPIO_SLEW_RATE_MASK;
1067 else
1068 reg &= ~THB_GPIO_SLEW_RATE_MASK;
1069
1070 return thb_gpio_write_reg(chip, pin, reg);
1071}
1072
1073static int thunderbay_pinconf_get_slew_rate(struct thunderbay_pinctrl *tpc,
1074 unsigned int pin, u32 *config)
1075{
1076 struct gpio_chip *chip = &tpc->chip;
1077 u32 reg;
1078
1079 reg = thb_gpio_read_reg(chip, pin);
1080 *config = ((reg & THB_GPIO_SLEW_RATE_MASK) > 0) ? 1 : 0;
1081
1082 return 0;
1083}
1084
1085static int thunderbay_pinconf_get(struct pinctrl_dev *pctldev, unsigned int pin,
1086 unsigned long *config)
1087{
1088 struct thunderbay_pinctrl *tpc = pinctrl_dev_get_drvdata(pctldev);
1089 enum pin_config_param param = pinconf_to_config_param(*config);
1090 u32 arg;
1091 int ret;
1092
1093 switch (param) {
1094 case PIN_CONFIG_BIAS_HIGH_IMPEDANCE:
1095 ret = thunderbay_pinconf_get_tristate(tpc, pin, &arg);
1096 break;
1097
1098 case PIN_CONFIG_BIAS_PULL_DOWN:
1099 ret = thunderbay_pinconf_get_pulldown(tpc, pin, &arg);
1100 break;
1101
1102 case PIN_CONFIG_BIAS_PULL_UP:
1103 ret = thunderbay_pinconf_get_pullup(tpc, pin, &arg);
1104 break;
1105
1106 case PIN_CONFIG_DRIVE_OPEN_DRAIN:
1107 ret = thunderbay_pinconf_get_opendrain(tpc, pin, &arg);
1108 break;
1109
1110 case PIN_CONFIG_DRIVE_PUSH_PULL:
1111 ret = thunderbay_pinconf_get_pushpull(tpc, pin, &arg);
1112 break;
1113
1114 case PIN_CONFIG_DRIVE_STRENGTH:
1115 ret = thunderbay_pinconf_get_drivestrength(tpc, pin, &arg);
1116 break;
1117
1118 case PIN_CONFIG_INPUT_SCHMITT_ENABLE:
1119 ret = thunderbay_pinconf_get_schmitt(tpc, pin, &arg);
1120 break;
1121
1122 case PIN_CONFIG_SLEW_RATE:
1123 ret = thunderbay_pinconf_get_slew_rate(tpc, pin, &arg);
1124 break;
1125
1126 default:
1127 return -ENOTSUPP;
1128 }
1129
1130 *config = pinconf_to_config_packed(param, arg);
1131
1132 return ret;
1133}
1134
1135static int thunderbay_pinconf_set(struct pinctrl_dev *pctldev, unsigned int pin,
1136 unsigned long *configs, unsigned int num_configs)
1137{
1138 struct thunderbay_pinctrl *tpc = pinctrl_dev_get_drvdata(pctldev);
1139 enum pin_config_param param;
1140 unsigned int pinconf;
1141 int ret = 0;
1142 u32 arg;
1143
1144 for (pinconf = 0; pinconf < num_configs; pinconf++) {
1145 param = pinconf_to_config_param(configs[pinconf]);
1146 arg = pinconf_to_config_argument(configs[pinconf]);
1147
1148 switch (param) {
1149 case PIN_CONFIG_BIAS_HIGH_IMPEDANCE:
1150 ret = thunderbay_pinconf_set_tristate(tpc, pin, arg);
1151 break;
1152
1153 case PIN_CONFIG_BIAS_PULL_DOWN:
1154 ret = thunderbay_pinconf_set_pulldown(tpc, pin, arg);
1155 break;
1156
1157 case PIN_CONFIG_BIAS_PULL_UP:
1158 ret = thunderbay_pinconf_set_pullup(tpc, pin, arg);
1159 break;
1160
1161 case PIN_CONFIG_DRIVE_OPEN_DRAIN:
1162 ret = thunderbay_pinconf_set_opendrain(tpc, pin, arg);
1163 break;
1164
1165 case PIN_CONFIG_DRIVE_PUSH_PULL:
1166 ret = thunderbay_pinconf_set_pushpull(tpc, pin, arg);
1167 break;
1168
1169 case PIN_CONFIG_DRIVE_STRENGTH:
1170 ret = thunderbay_pinconf_set_drivestrength(tpc, pin, arg);
1171 break;
1172
1173 case PIN_CONFIG_INPUT_SCHMITT_ENABLE:
1174 ret = thunderbay_pinconf_set_schmitt(tpc, pin, arg);
1175 break;
1176
1177 case PIN_CONFIG_SLEW_RATE:
1178 ret = thunderbay_pinconf_set_slew_rate(tpc, pin, arg);
1179 break;
1180
1181 default:
1182 return -ENOTSUPP;
1183 }
1184 }
1185 return ret;
1186}
1187
1188static const struct pinctrl_ops thunderbay_pctlops = {
1189 .get_groups_count = pinctrl_generic_get_group_count,
1190 .get_group_name = pinctrl_generic_get_group_name,
1191 .get_group_pins = pinctrl_generic_get_group_pins,
1192 .dt_node_to_map = pinconf_generic_dt_node_to_map_all,
1193 .dt_free_map = pinconf_generic_dt_free_map,
1194};
1195
1196static const struct pinmux_ops thunderbay_pmxops = {
1197 .get_functions_count = pinmux_generic_get_function_count,
1198 .get_function_name = pinmux_generic_get_function_name,
1199 .get_function_groups = pinmux_generic_get_function_groups,
1200 .set_mux = thb_pinctrl_set_mux,
1201 .gpio_request_enable = thunderbay_request_gpio,
1202 .gpio_disable_free = thunderbay_free_gpio,
1203};
1204
1205static const struct pinconf_ops thunderbay_confops = {
1206 .is_generic = true,
1207 .pin_config_get = thunderbay_pinconf_get,
1208 .pin_config_set = thunderbay_pinconf_set,
1209};
1210
1211static struct pinctrl_desc thunderbay_pinctrl_desc = {
1212 .name = "thunderbay-pinmux",
1213 .pctlops = &thunderbay_pctlops,
1214 .pmxops = &thunderbay_pmxops,
1215 .confops = &thunderbay_confops,
1216 .owner = THIS_MODULE,
1217};
1218
1219static const struct of_device_id thunderbay_pinctrl_match[] = {
1220 {
1221 .compatible = "intel,thunderbay-pinctrl",
1222 .data = &thunderbay_data
1223 },
1224 {}
1225};
1226
1227static int thunderbay_pinctrl_probe(struct platform_device *pdev)
1228{
1229 const struct of_device_id *of_id;
1230 struct device *dev = &pdev->dev;
1231 struct thunderbay_pinctrl *tpc;
1232 struct resource *iomem;
1233 int ret;
1234
1235 of_id = of_match_node(thunderbay_pinctrl_match, pdev->dev.of_node);
1236 if (!of_id)
1237 return -ENODEV;
1238
1239 tpc = devm_kzalloc(dev, sizeof(*tpc), GFP_KERNEL);
1240 if (!tpc)
1241 return -ENOMEM;
1242
1243 tpc->dev = dev;
1244 tpc->soc = of_id->data;
1245
1246 iomem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
1247 if (!iomem)
1248 return -ENXIO;
1249
1250 tpc->base0 = devm_ioremap_resource(dev, iomem);
1251 if (IS_ERR(tpc->base0))
1252 return PTR_ERR(tpc->base0);
1253
1254 thunderbay_pinctrl_desc.pins = tpc->soc->pins;
1255 thunderbay_pinctrl_desc.npins = tpc->soc->npins;
1256
1257 /* Register pinctrl */
1258 tpc->pctrl = devm_pinctrl_register(dev, &thunderbay_pinctrl_desc, tpc);
1259 if (IS_ERR(tpc->pctrl))
1260 return PTR_ERR(tpc->pctrl);
1261
1262 /* Setup pinmux groups */
1263 ret = thunderbay_build_groups(tpc);
1264 if (ret)
1265 return ret;
1266
1267 /* Setup pinmux functions */
1268 ret = thunderbay_build_functions(tpc);
1269 if (ret)
1270 return ret;
1271
1272 /* Setup GPIO */
1273 ret = thunderbay_gpiochip_probe(tpc);
1274 if (ret < 0)
1275 return ret;
1276
1277 platform_set_drvdata(pdev, tpc);
1278
1279 return 0;
1280}
1281
1282static int thunderbay_pinctrl_remove(struct platform_device *pdev)
1283{
1284 /* thunderbay_pinctrl_remove function to clear the assigned memory */
1285 return 0;
1286}
1287
1288static struct platform_driver thunderbay_pinctrl_driver = {
1289 .driver = {
1290 .name = "thunderbay-pinctrl",
1291 .of_match_table = thunderbay_pinctrl_match,
1292 },
1293 .probe = thunderbay_pinctrl_probe,
1294 .remove = thunderbay_pinctrl_remove,
1295};
1296
1297builtin_platform_driver(thunderbay_pinctrl_driver);
1298
1299MODULE_AUTHOR("Lakshmi Sowjanya D <lakshmi.sowjanya.d@intel.com>");
1300MODULE_AUTHOR("Kiran Kumar S <kiran.kumar1.s@intel.com>");
1301MODULE_DESCRIPTION("Intel Thunder Bay Pinctrl/GPIO Driver");
1302MODULE_LICENSE("GPL v2");