This source file includes following definitions.
- u8_pin2mask
- u8_gpio_get
- u8_gpio_set
- u8_gpio_dir_in
- u8_gpio_dir_out
- u8_gpio_save_regs
- u8_simple_gpiochip_add
- simple_gpiochip_init
1
2
3
4
5
6
7
8
9
10 #include <linux/init.h>
11 #include <linux/kernel.h>
12 #include <linux/spinlock.h>
13 #include <linux/types.h>
14 #include <linux/ioport.h>
15 #include <linux/io.h>
16 #include <linux/of.h>
17 #include <linux/of_gpio.h>
18 #include <linux/gpio/driver.h>
19 #include <linux/slab.h>
20 #include <asm/prom.h>
21 #include "simple_gpio.h"
22
23 struct u8_gpio_chip {
24 struct of_mm_gpio_chip mm_gc;
25 spinlock_t lock;
26
27
28 u8 data;
29 };
30
31 static u8 u8_pin2mask(unsigned int pin)
32 {
33 return 1 << (8 - 1 - pin);
34 }
35
36 static int u8_gpio_get(struct gpio_chip *gc, unsigned int gpio)
37 {
38 struct of_mm_gpio_chip *mm_gc = to_of_mm_gpio_chip(gc);
39
40 return !!(in_8(mm_gc->regs) & u8_pin2mask(gpio));
41 }
42
43 static void u8_gpio_set(struct gpio_chip *gc, unsigned int gpio, int val)
44 {
45 struct of_mm_gpio_chip *mm_gc = to_of_mm_gpio_chip(gc);
46 struct u8_gpio_chip *u8_gc = gpiochip_get_data(gc);
47 unsigned long flags;
48
49 spin_lock_irqsave(&u8_gc->lock, flags);
50
51 if (val)
52 u8_gc->data |= u8_pin2mask(gpio);
53 else
54 u8_gc->data &= ~u8_pin2mask(gpio);
55
56 out_8(mm_gc->regs, u8_gc->data);
57
58 spin_unlock_irqrestore(&u8_gc->lock, flags);
59 }
60
61 static int u8_gpio_dir_in(struct gpio_chip *gc, unsigned int gpio)
62 {
63 return 0;
64 }
65
66 static int u8_gpio_dir_out(struct gpio_chip *gc, unsigned int gpio, int val)
67 {
68 u8_gpio_set(gc, gpio, val);
69 return 0;
70 }
71
72 static void u8_gpio_save_regs(struct of_mm_gpio_chip *mm_gc)
73 {
74 struct u8_gpio_chip *u8_gc =
75 container_of(mm_gc, struct u8_gpio_chip, mm_gc);
76
77 u8_gc->data = in_8(mm_gc->regs);
78 }
79
80 static int __init u8_simple_gpiochip_add(struct device_node *np)
81 {
82 int ret;
83 struct u8_gpio_chip *u8_gc;
84 struct of_mm_gpio_chip *mm_gc;
85 struct gpio_chip *gc;
86
87 u8_gc = kzalloc(sizeof(*u8_gc), GFP_KERNEL);
88 if (!u8_gc)
89 return -ENOMEM;
90
91 spin_lock_init(&u8_gc->lock);
92
93 mm_gc = &u8_gc->mm_gc;
94 gc = &mm_gc->gc;
95
96 mm_gc->save_regs = u8_gpio_save_regs;
97 gc->ngpio = 8;
98 gc->direction_input = u8_gpio_dir_in;
99 gc->direction_output = u8_gpio_dir_out;
100 gc->get = u8_gpio_get;
101 gc->set = u8_gpio_set;
102
103 ret = of_mm_gpiochip_add_data(np, mm_gc, u8_gc);
104 if (ret)
105 goto err;
106 return 0;
107 err:
108 kfree(u8_gc);
109 return ret;
110 }
111
112 void __init simple_gpiochip_init(const char *compatible)
113 {
114 struct device_node *np;
115
116 for_each_compatible_node(np, NULL, compatible) {
117 int ret;
118 struct resource r;
119
120 ret = of_address_to_resource(np, 0, &r);
121 if (ret)
122 goto err;
123
124 switch (resource_size(&r)) {
125 case 1:
126 ret = u8_simple_gpiochip_add(np);
127 if (ret)
128 goto err;
129 break;
130 default:
131
132
133
134
135
136 ret = -ENOSYS;
137 goto err;
138 }
139 continue;
140 err:
141 pr_err("%pOF: registration failed, status %d\n", np, ret);
142 }
143 }