xref: /openbmc/u-boot/drivers/gpio/xilinx_gpio.c (revision b1e6c4c3)
1 /*
2  * Copyright (c) 2013 Xilinx, Michal Simek
3  *
4  * See file CREDITS for list of people who contributed to this
5  * project.
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License as
9  * published by the Free Software Foundation; either version 2 of
10  * the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
20  * MA 02111-1307 USA
21  */
22 
23 #include <common.h>
24 #include <errno.h>
25 #include <malloc.h>
26 #include <linux/list.h>
27 #include <asm/io.h>
28 #include <asm/gpio.h>
29 
30 static LIST_HEAD(gpio_list);
31 
32 enum gpio_direction {
33 	GPIO_DIRECTION_OUT = 0,
34 	GPIO_DIRECTION_IN = 1,
35 };
36 
37 /* Gpio simple map */
38 struct gpio_regs {
39 	u32 gpiodata;
40 	u32 gpiodir;
41 };
42 
43 #define GPIO_NAME_SIZE	10
44 
45 struct gpio_names {
46 	char name[GPIO_NAME_SIZE];
47 };
48 
49 /* Initialized, rxbd_current, rx_first_buf must be 0 after init */
50 struct xilinx_gpio_priv {
51 	struct gpio_regs *regs;
52 	u32 gpio_min;
53 	u32 gpio_max;
54 	u32 gpiodata_store;
55 	char name[GPIO_NAME_SIZE];
56 	struct list_head list;
57 	struct gpio_names *gpio_name;
58 };
59 
60 /* Store number of allocated gpio pins */
61 static u32 xilinx_gpio_max;
62 
63 /* Get associated gpio controller */
64 static struct xilinx_gpio_priv *gpio_get_controller(unsigned gpio)
65 {
66 	struct list_head *entry;
67 	struct xilinx_gpio_priv *priv = NULL;
68 
69 	list_for_each(entry, &gpio_list) {
70 		priv = list_entry(entry, struct xilinx_gpio_priv, list);
71 		if (gpio >= priv->gpio_min && gpio <= priv->gpio_max) {
72 			debug("%s: reg: %x, min-max: %d-%d\n", __func__,
73 			      (u32)priv->regs, priv->gpio_min, priv->gpio_max);
74 			return priv;
75 		}
76 	}
77 	puts("!!!Can't get gpio controller!!!\n");
78 	return NULL;
79 }
80 
81 /* Get gpio pin name if used/setup */
82 static char *get_name(unsigned gpio)
83 {
84 	u32 gpio_priv;
85 	struct xilinx_gpio_priv *priv;
86 
87 	debug("%s\n", __func__);
88 
89 	priv = gpio_get_controller(gpio);
90 	if (priv) {
91 		gpio_priv = gpio - priv->gpio_min;
92 
93 		return *priv->gpio_name[gpio_priv].name ?
94 			priv->gpio_name[gpio_priv].name : "UNKNOWN";
95 	}
96 	return "UNKNOWN";
97 }
98 
99 /* Get output value */
100 static int gpio_get_output_value(unsigned gpio)
101 {
102 	u32 val, gpio_priv;
103 	struct xilinx_gpio_priv *priv = gpio_get_controller(gpio);
104 
105 	if (priv) {
106 		gpio_priv = gpio - priv->gpio_min;
107 		val = !!(priv->gpiodata_store & (1 << gpio_priv));
108 		debug("%s: reg: %x, gpio_no: %d, dir: %d\n", __func__,
109 		      (u32)priv->regs, gpio_priv, val);
110 
111 		return val;
112 	}
113 	return -1;
114 }
115 
116 /* Get input value */
117 static int gpio_get_input_value(unsigned gpio)
118 {
119 	u32 val, gpio_priv;
120 	struct gpio_regs *regs;
121 	struct xilinx_gpio_priv *priv = gpio_get_controller(gpio);
122 
123 	if (priv) {
124 		regs = priv->regs;
125 		gpio_priv = gpio - priv->gpio_min;
126 		val = readl(&regs->gpiodata);
127 		val = !!(val & (1 << gpio_priv));
128 		debug("%s: reg: %x, gpio_no: %d, dir: %d\n", __func__,
129 		      (u32)priv->regs, gpio_priv, val);
130 
131 		return val;
132 	}
133 	return -1;
134 }
135 
136 /* Set gpio direction */
137 static int gpio_set_direction(unsigned gpio, enum gpio_direction direction)
138 {
139 	u32 val, gpio_priv;
140 	struct gpio_regs *regs;
141 	struct xilinx_gpio_priv *priv = gpio_get_controller(gpio);
142 
143 	if (priv) {
144 		regs = priv->regs;
145 		val = readl(&regs->gpiodir);
146 
147 		gpio_priv = gpio - priv->gpio_min;
148 		if (direction == GPIO_DIRECTION_OUT)
149 			val &= ~(1 << gpio_priv);
150 		else
151 			val |= 1 << gpio_priv;
152 
153 		writel(val, &regs->gpiodir);
154 		debug("%s: reg: %x, gpio_no: %d, dir: %d\n", __func__,
155 		      (u32)priv->regs, gpio_priv, val);
156 
157 		return 0;
158 	}
159 
160 	return -1;
161 }
162 
163 /* Get gpio direction */
164 static int gpio_get_direction(unsigned gpio)
165 {
166 	u32 val, gpio_priv;
167 	struct gpio_regs *regs;
168 	struct xilinx_gpio_priv *priv = gpio_get_controller(gpio);
169 
170 	if (priv) {
171 		regs = priv->regs;
172 		gpio_priv = gpio - priv->gpio_min;
173 		val = readl(&regs->gpiodir);
174 		val = !!(val & (1 << gpio_priv));
175 		debug("%s: reg: %x, gpio_no: %d, dir: %d\n", __func__,
176 		      (u32)priv->regs, gpio_priv, val);
177 
178 		return val;
179 	}
180 
181 	return -1;
182 }
183 
184 /*
185  * Get input value
186  * for example gpio setup to output only can't get input value
187  * which is breaking gpio toggle command
188  */
189 int gpio_get_value(unsigned gpio)
190 {
191 	u32 val;
192 
193 	if (gpio_get_direction(gpio) == GPIO_DIRECTION_OUT)
194 		val = gpio_get_output_value(gpio);
195 	else
196 		val = gpio_get_input_value(gpio);
197 
198 	return val;
199 }
200 
201 /* Set output value */
202 static int gpio_set_output_value(unsigned gpio, int value)
203 {
204 	u32 val, gpio_priv;
205 	struct gpio_regs *regs;
206 	struct xilinx_gpio_priv *priv = gpio_get_controller(gpio);
207 
208 	if (priv) {
209 		regs = priv->regs;
210 		gpio_priv = gpio - priv->gpio_min;
211 		val = priv->gpiodata_store;
212 		if (value)
213 			val |= 1 << gpio_priv;
214 		else
215 			val &= ~(1 << gpio_priv);
216 
217 		writel(val, &regs->gpiodata);
218 		debug("%s: reg: %x, gpio_no: %d, output_val: %d\n", __func__,
219 		      (u32)priv->regs, gpio_priv, val);
220 		priv->gpiodata_store = val;
221 
222 		return 0;
223 	}
224 
225 	return -1;
226 }
227 
228 int gpio_set_value(unsigned gpio, int value)
229 {
230 	if (gpio_get_direction(gpio) == GPIO_DIRECTION_OUT)
231 		return gpio_set_output_value(gpio, value);
232 
233 	return -1;
234 }
235 
236 /* Set GPIO as input */
237 int gpio_direction_input(unsigned gpio)
238 {
239 	debug("%s\n", __func__);
240 	return gpio_set_direction(gpio, GPIO_DIRECTION_IN);
241 }
242 
243 /* Setup GPIO as output and set output value */
244 int gpio_direction_output(unsigned gpio, int value)
245 {
246 	int ret = gpio_set_direction(gpio, GPIO_DIRECTION_OUT);
247 
248 	debug("%s\n", __func__);
249 
250 	if (ret < 0)
251 		return ret;
252 
253 	return gpio_set_output_value(gpio, value);
254 }
255 
256 /* Show gpio status */
257 void gpio_info(void)
258 {
259 	unsigned gpio;
260 
261 	struct list_head *entry;
262 	struct xilinx_gpio_priv *priv = NULL;
263 
264 	list_for_each(entry, &gpio_list) {
265 		priv = list_entry(entry, struct xilinx_gpio_priv, list);
266 		printf("\n%s: %s/%x (%d-%d)\n", __func__, priv->name,
267 		       (u32)priv->regs, priv->gpio_min, priv->gpio_max);
268 
269 		for (gpio = priv->gpio_min; gpio <= priv->gpio_max; gpio++) {
270 			printf("GPIO_%d:\t%s is an ", gpio, get_name(gpio));
271 			if (gpio_get_direction(gpio) == GPIO_DIRECTION_OUT)
272 				printf("OUTPUT value = %d\n",
273 				       gpio_get_output_value(gpio));
274 			else
275 				printf("INPUT value = %d\n",
276 				       gpio_get_input_value(gpio));
277 		}
278 	}
279 }
280 
281 int gpio_request(unsigned gpio, const char *label)
282 {
283 	u32 gpio_priv;
284 	struct xilinx_gpio_priv *priv;
285 
286 	if (gpio >= xilinx_gpio_max)
287 		return -EINVAL;
288 
289 	priv = gpio_get_controller(gpio);
290 	if (priv) {
291 		gpio_priv = gpio - priv->gpio_min;
292 
293 		if (label != NULL) {
294 			strncpy(priv->gpio_name[gpio_priv].name, label,
295 				GPIO_NAME_SIZE);
296 			priv->gpio_name[gpio_priv].name[GPIO_NAME_SIZE - 1] =
297 					'\0';
298 		}
299 		return 0;
300 	}
301 
302 	return -1;
303 }
304 
305 int gpio_free(unsigned gpio)
306 {
307 	u32 gpio_priv;
308 	struct xilinx_gpio_priv *priv;
309 
310 	if (gpio >= xilinx_gpio_max)
311 		return -EINVAL;
312 
313 	priv = gpio_get_controller(gpio);
314 	if (priv) {
315 		gpio_priv = gpio - priv->gpio_min;
316 		priv->gpio_name[gpio_priv].name[0] = '\0';
317 
318 		/* Do nothing here */
319 		return 0;
320 	}
321 
322 	return -1;
323 }
324 
325 int gpio_alloc(u32 baseaddr, const char *name, u32 gpio_no)
326 {
327 	struct xilinx_gpio_priv *priv;
328 
329 	priv = calloc(1, sizeof(struct xilinx_gpio_priv));
330 
331 	/* Setup gpio name */
332 	if (name != NULL) {
333 		strncpy(priv->name, name, GPIO_NAME_SIZE);
334 		priv->name[GPIO_NAME_SIZE - 1] = '\0';
335 	}
336 	priv->regs = (struct gpio_regs *)baseaddr;
337 
338 	priv->gpio_min = xilinx_gpio_max;
339 	xilinx_gpio_max = priv->gpio_min + gpio_no;
340 	priv->gpio_max = xilinx_gpio_max - 1;
341 
342 	priv->gpio_name = calloc(gpio_no, sizeof(struct gpio_names));
343 
344 	INIT_LIST_HEAD(&priv->list);
345 	list_add_tail(&priv->list, &gpio_list);
346 
347 	printf("%s: Add %s (%d-%d)\n", __func__, name,
348 	       priv->gpio_min, priv->gpio_max);
349 
350 	/* Return the first gpio allocated for this device */
351 	return priv->gpio_min;
352 }
353 
354 /* Dual channel gpio is one IP with two independent channels */
355 int gpio_alloc_dual(u32 baseaddr, const char *name, u32 gpio_no0, u32 gpio_no1)
356 {
357 	int ret;
358 
359 	ret = gpio_alloc(baseaddr, name, gpio_no0);
360 	gpio_alloc(baseaddr + 8, strcat((char *)name, "_1"), gpio_no1);
361 
362 	/* Return the first gpio allocated for this device */
363 	return ret;
364 }
365