Motion-PRO: Code cleanup, fix of a typo in OF_STDOUT_PATH.
[platform/kernel/u-boot.git] / cpu / at32ap / pio.c
1 /*
2  * Copyright (C) 2006 Atmel Corporation
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 #include <common.h>
23
24 #include <asm/errno.h>
25 #include <asm/io.h>
26 #include <asm/arch/platform.h>
27
28 #include "pio2.h"
29
30 struct pio_state {
31         const struct device *dev;
32         u32 alloc_mask;
33 };
34
35 static struct pio_state pio_state[CFG_NR_PIOS];
36
37 int gpio_set_func(enum device_id gpio_devid, unsigned int start,
38                   unsigned int nr_pins, enum gpio_func func)
39 {
40         const struct device *gpio;
41         struct pio_state *state;
42         u32 mask;
43
44         state = &pio_state[gpio_devid - DEVICE_PIOA];
45
46         gpio = get_device(gpio_devid);
47         if (!gpio)
48                 return -EBUSY;
49
50         state->dev = gpio;
51         mask = ((1 << nr_pins) - 1) << start;
52
53         if (mask & state->alloc_mask) {
54                 put_device(gpio);
55                 return -EBUSY;
56         }
57         state->alloc_mask |= mask;
58
59         switch (func) {
60         case GPIO_FUNC_GPIO:
61                 /* TODO */
62                 return -EINVAL;
63         case GPIO_FUNC_A:
64                 pio2_writel(gpio, ASR, mask);
65                 pio2_writel(gpio, PDR, mask);
66                 pio2_writel(gpio, PUDR, mask);
67                 break;
68         case GPIO_FUNC_B:
69                 pio2_writel(gpio, BSR, mask);
70                 pio2_writel(gpio, PDR, mask);
71                 pio2_writel(gpio, PUDR, mask);
72                 break;
73         }
74
75         return 0;
76 }
77
78 void gpio_free(enum device_id gpio_devid, unsigned int start,
79                unsigned int nr_pins)
80 {
81         const struct device *gpio;
82         struct pio_state *state;
83         u32 mask;
84
85         state = &pio_state[gpio_devid - DEVICE_PIOA];
86         gpio = state->dev;
87         mask = ((1 << nr_pins) - 1) << start;
88
89         pio2_writel(gpio, ODR, mask);
90         pio2_writel(gpio, PER, mask);
91
92         state->alloc_mask &= ~mask;
93         put_device(gpio);
94 }