diff options
author | Jonathan Cameron <jic23@cam.ac.uk> | 2009-08-18 13:06:20 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2009-09-15 15:02:24 -0400 |
commit | d1325cf45077bd27db3271dfc320c40bf65a8a07 (patch) | |
tree | 59954caa5fada2767cc0647828a4b621c99b8958 | |
parent | 847ec80bbaa76aae41062d6802cea9c1b2289f14 (diff) |
Staging: IIO: max1363 ADC driver
Core support for MAX1361, MAX1362, MAX1363, MAX1364,
MAX1136, MAX1137, MAX1138, MAX1139, MAX1236, MAX1237,
MAX1238, MAX1239.
Ring buffer support later in series.
Signed-off-by: Jonathan Cameron <jic23@cam.ac.uk>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
-rw-r--r-- | drivers/staging/iio/Kconfig | 5 | ||||
-rw-r--r-- | drivers/staging/iio/Makefile | 2 | ||||
-rw-r--r-- | drivers/staging/iio/adc/Kconfig | 13 | ||||
-rw-r--r-- | drivers/staging/iio/adc/Makefile | 7 | ||||
-rw-r--r-- | drivers/staging/iio/adc/max1363.h | 257 | ||||
-rw-r--r-- | drivers/staging/iio/adc/max1363_core.c | 623 |
6 files changed, 907 insertions, 0 deletions
diff --git a/drivers/staging/iio/Kconfig b/drivers/staging/iio/Kconfig index 09e4101939ef..d7b3107823f6 100644 --- a/drivers/staging/iio/Kconfig +++ b/drivers/staging/iio/Kconfig | |||
@@ -9,3 +9,8 @@ menuconfig IIO | |||
9 | drivers for many different types of embedded sensors using a | 9 | drivers for many different types of embedded sensors using a |
10 | number of different physical interfaces (i2c, spi etc). See | 10 | number of different physical interfaces (i2c, spi etc). See |
11 | Documentation/industrialio for more information. | 11 | Documentation/industrialio for more information. |
12 | if IIO | ||
13 | |||
14 | source "drivers/staging/iio/adc/Kconfig" | ||
15 | |||
16 | endif # IIO | ||
diff --git a/drivers/staging/iio/Makefile b/drivers/staging/iio/Makefile index 92b462a125e8..9d11f640d20b 100644 --- a/drivers/staging/iio/Makefile +++ b/drivers/staging/iio/Makefile | |||
@@ -4,3 +4,5 @@ | |||
4 | 4 | ||
5 | obj-$(CONFIG_IIO) += industrialio.o | 5 | obj-$(CONFIG_IIO) += industrialio.o |
6 | industrialio-y := industrialio-core.o | 6 | industrialio-y := industrialio-core.o |
7 | |||
8 | obj-y += adc/ \ No newline at end of file | ||
diff --git a/drivers/staging/iio/adc/Kconfig b/drivers/staging/iio/adc/Kconfig new file mode 100644 index 000000000000..b8c2858585f9 --- /dev/null +++ b/drivers/staging/iio/adc/Kconfig | |||
@@ -0,0 +1,13 @@ | |||
1 | # | ||
2 | # ADC drivers | ||
3 | # | ||
4 | comment "Analog to digital convertors" | ||
5 | |||
6 | config MAX1363 | ||
7 | tristate "MAXIM max1363 ADC driver" | ||
8 | depends on I2C | ||
9 | help | ||
10 | Say yes here to build support for many MAXIM i2c analog to digital | ||
11 | convertors (ADC). (max1361, max1362, max1363, max1364, max1136, | ||
12 | max1136, max1137, max1138, max1139, max1236, max1237, max11238, | ||
13 | max1239) Provides direct access via sysfs. | ||
diff --git a/drivers/staging/iio/adc/Makefile b/drivers/staging/iio/adc/Makefile new file mode 100644 index 000000000000..2a37feed4add --- /dev/null +++ b/drivers/staging/iio/adc/Makefile | |||
@@ -0,0 +1,7 @@ | |||
1 | |||
2 | # Makefile for industrial I/O ADC drivers | ||
3 | # | ||
4 | |||
5 | max1363-y := max1363_core.o | ||
6 | |||
7 | obj-$(CONFIG_MAX1363) += max1363.o | ||
diff --git a/drivers/staging/iio/adc/max1363.h b/drivers/staging/iio/adc/max1363.h new file mode 100644 index 000000000000..a9d5c21a6c3c --- /dev/null +++ b/drivers/staging/iio/adc/max1363.h | |||
@@ -0,0 +1,257 @@ | |||
1 | #ifndef _MAX1363_H_ | ||
2 | #define _MAX1363_H_ | ||
3 | |||
4 | #define MAX1363_SETUP_BYTE(a) ((a) | 0x80) | ||
5 | |||
6 | /* There is a fair bit more defined here than currently | ||
7 | * used, but the intention is to support everything these | ||
8 | * chips do in the long run */ | ||
9 | |||
10 | /* see data sheets */ | ||
11 | /* max1363 and max1236, max1237, max1238, max1239 */ | ||
12 | #define MAX1363_SETUP_AIN3_IS_AIN3_REF_IS_VDD 0x00 | ||
13 | #define MAX1363_SETUP_AIN3_IS_REF_EXT_TO_REF 0x20 | ||
14 | #define MAX1363_SETUP_AIN3_IS_AIN3_REF_IS_INT 0x40 | ||
15 | #define MAX1363_SETUP_AIN3_IS_REF_REF_IS_INT 0x60 | ||
16 | #define MAX1363_SETUP_POWER_UP_INT_REF 0x10 | ||
17 | #define MAX1363_SETUP_POWER_DOWN_INT_REF 0x00 | ||
18 | |||
19 | /* think about includeing max11600 etc - more settings */ | ||
20 | #define MAX1363_SETUP_EXT_CLOCK 0x08 | ||
21 | #define MAX1363_SETUP_INT_CLOCK 0x00 | ||
22 | #define MAX1363_SETUP_UNIPOLAR 0x00 | ||
23 | #define MAX1363_SETUP_BIPOLAR 0x04 | ||
24 | #define MAX1363_SETUP_RESET 0x00 | ||
25 | #define MAX1363_SETUP_NORESET 0x02 | ||
26 | /* max1363 only - though don't care on others. | ||
27 | * For now monitor modes are not implemented as the relevant | ||
28 | * line is not connected on my test board. | ||
29 | * The definitions are here as I intend to add this soon. | ||
30 | */ | ||
31 | #define MAX1363_SETUP_MONITOR_SETUP 0x01 | ||
32 | |||
33 | /* Specific to the max1363 */ | ||
34 | #define MAX1363_MON_RESET_CHAN(a) (1 << ((a) + 4)) | ||
35 | #define MAX1363_MON_CONV_RATE_133ksps 0 | ||
36 | #define MAX1363_MON_CONV_RATE_66_5ksps 0x02 | ||
37 | #define MAX1363_MON_CONV_RATE_33_3ksps 0x04 | ||
38 | #define MAX1363_MON_CONV_RATE_16_6ksps 0x06 | ||
39 | #define MAX1363_MON_CONV_RATE_8_3ksps 0x08 | ||
40 | #define MAX1363_MON_CONV_RATE_4_2ksps 0x0A | ||
41 | #define MAX1363_MON_CONV_RATE_2_0ksps 0x0C | ||
42 | #define MAX1363_MON_CONV_RATE_1_0ksps 0x0E | ||
43 | #define MAX1363_MON_INT_ENABLE 0x01 | ||
44 | |||
45 | /* defined for readability reasons */ | ||
46 | /* All chips */ | ||
47 | #define MAX1363_CONFIG_BYTE(a) ((a)) | ||
48 | |||
49 | #define MAX1363_CONFIG_SE 0x01 | ||
50 | #define MAX1363_CONFIG_DE 0x00 | ||
51 | #define MAX1363_CONFIG_SCAN_TO_CS 0x00 | ||
52 | #define MAX1363_CONFIG_SCAN_SINGLE_8 0x20 | ||
53 | #define MAX1363_CONFIG_SCAN_MONITOR_MODE 0x40 | ||
54 | #define MAX1363_CONFIG_SCAN_SINGLE_1 0x60 | ||
55 | /* max123{6-9} only */ | ||
56 | #define MAX1236_SCAN_MID_TO_CHANNEL 0x40 | ||
57 | |||
58 | /* max1363 only - merely part of channel selects or don't care for others*/ | ||
59 | #define MAX1363_CONFIG_EN_MON_MODE_READ 0x18 | ||
60 | |||
61 | #define MAX1363_CHANNEL_SEL(a) ((a) << 1) | ||
62 | |||
63 | /* max1363 strictly 0x06 - but doesn't matter */ | ||
64 | #define MAX1363_CHANNEL_SEL_MASK 0x1E | ||
65 | #define MAX1363_SCAN_MASK 0x60 | ||
66 | #define MAX1363_SE_DE_MASK 0x01 | ||
67 | |||
68 | /** | ||
69 | * struct max1363_mode - scan mode information | ||
70 | * @name: Name used to identify the scan mode. | ||
71 | * @conf: The corresponding value of the configuration register | ||
72 | * @numvals: The number of values returned by a single scan | ||
73 | */ | ||
74 | struct max1363_mode { | ||
75 | const char *name; | ||
76 | int8_t conf; | ||
77 | int numvals; | ||
78 | }; | ||
79 | |||
80 | #define MAX1363_MODE_SINGLE(_num) { \ | ||
81 | .name = #_num, \ | ||
82 | .conf = MAX1363_CHANNEL_SEL(_num) \ | ||
83 | | MAX1363_CONFIG_SCAN_SINGLE_1 \ | ||
84 | | MAX1363_CONFIG_SE, \ | ||
85 | .numvals = 1, \ | ||
86 | } | ||
87 | |||
88 | #define MAX1363_MODE_SINGLE_TIMES_8(_num) { \ | ||
89 | .name = #_num"x8", \ | ||
90 | .conf = MAX1363_CHANNEL_SEL(_num) \ | ||
91 | | MAX1363_CONFIG_SCAN_SINGLE_8 \ | ||
92 | | MAX1363_CONFIG_SE, \ | ||
93 | .numvals = 8, \ | ||
94 | } | ||
95 | |||
96 | #define MAX1363_MODE_SCAN_TO_CHANNEL(_num) { \ | ||
97 | .name = "0..."#_num, \ | ||
98 | .conf = MAX1363_CHANNEL_SEL(_num) \ | ||
99 | | MAX1363_CONFIG_SCAN_TO_CS \ | ||
100 | | MAX1363_CONFIG_SE, \ | ||
101 | .numvals = _num + 1, \ | ||
102 | } | ||
103 | |||
104 | |||
105 | /* note not available for max1363 hence naming */ | ||
106 | #define MAX1236_MODE_SCAN_MID_TO_CHANNEL(_mid, _num) { \ | ||
107 | .name = #_mid"..."#_num, \ | ||
108 | .conf = MAX1363_CHANNEL_SEL(_num) \ | ||
109 | | MAX1236_SCAN_MID_TO_CHANNEL \ | ||
110 | | MAX1363_CONFIG_SE, \ | ||
111 | .numvals = _num - _mid + 1 \ | ||
112 | } | ||
113 | |||
114 | #define MAX1363_MODE_DIFF_SINGLE(_nump, _numm) { \ | ||
115 | .name = #_nump"-"#_numm, \ | ||
116 | .conf = MAX1363_CHANNEL_SEL(_nump) \ | ||
117 | | MAX1363_CONFIG_SCAN_SINGLE_1 \ | ||
118 | | MAX1363_CONFIG_DE, \ | ||
119 | .numvals = 1, \ | ||
120 | } | ||
121 | |||
122 | #define MAX1363_MODE_DIFF_SINGLE_TIMES_8(_nump, _numm) { \ | ||
123 | .name = #_nump"-"#_numm, \ | ||
124 | .conf = MAX1363_CHANNEL_SEL(_nump) \ | ||
125 | | MAX1363_CONFIG_SCAN_SINGLE_8 \ | ||
126 | | MAX1363_CONFIG_DE, \ | ||
127 | .numvals = 1, \ | ||
128 | } | ||
129 | |||
130 | /* Can't think how to automate naming so specify for now */ | ||
131 | #define MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(_name, _num, _numvals) { \ | ||
132 | .name = #_name, \ | ||
133 | .conf = MAX1363_CHANNEL_SEL(_num) \ | ||
134 | | MAX1363_CONFIG_SCAN_TO_CS \ | ||
135 | | MAX1363_CONFIG_DE, \ | ||
136 | .numvals = _numvals, \ | ||
137 | } | ||
138 | |||
139 | /* note only available for max1363 hence naming */ | ||
140 | #define MAX1236_MODE_DIFF_SCAN_MID_TO_CHANNEL_NAMED(_name, _num, _numvals) { \ | ||
141 | .name = #_name, \ | ||
142 | .conf = MAX1363_CHANNEL_SEL(_num) \ | ||
143 | | MAX1236_SCAN_MID_TO_CHANNEL \ | ||
144 | | MAX1363_CONFIG_SE, \ | ||
145 | .numvals = _numvals, \ | ||
146 | } | ||
147 | |||
148 | /* Not currently handled */ | ||
149 | #define MAX1363_MODE_MONITOR { \ | ||
150 | .name = "monitor", \ | ||
151 | .conf = MAX1363_CHANNEL_SEL(3) \ | ||
152 | | MAX1363_CONFIG_SCAN_MONITOR_MODE \ | ||
153 | | MAX1363_CONFIG_SE, \ | ||
154 | .numvals = 10, \ | ||
155 | } | ||
156 | |||
157 | /* This may seem an overly long winded way to do this, but at least it makes | ||
158 | * clear what all the various options actually do. Alternative suggestions | ||
159 | * that don't require user to have intimate knowledge of the chip welcomed. | ||
160 | */ | ||
161 | |||
162 | /* This must be maintained along side the max1363_mode_table in max1363_core */ | ||
163 | enum max1363_modes { | ||
164 | /* Single read of a single channel */ | ||
165 | _s0, _s1, _s2, _s3, _s4, _s5, _s6, _s7, _s8, _s9, _s10, _s11, | ||
166 | /* Eight reads of a single channel */ | ||
167 | se0, se1, se2, se3, se4, se5, se6, se7, se8, se9, se10, se11, | ||
168 | /* Scan to channel */ | ||
169 | s0to1, s0to2, s0to3, s0to4, s0to5, s0to6, | ||
170 | s0to7, s0to8, s0to9, s0to10, s0to11, | ||
171 | /* Differential single read */ | ||
172 | d0m1, d2m3, d4m5, d6m7, d8m9, d10m11, | ||
173 | d1m0, d3m2, d5m4, d7m6, d9m8, d11m10, | ||
174 | /* Differential single read 8 times */ | ||
175 | de0m1, de2m3, de4m5, de6m7, de8m9, de10m11, | ||
176 | de1m0, de3m2, de5m4, de7m6, de9m8, de11m10, | ||
177 | /* Differential scan to channel */ | ||
178 | d0m1to2m3, d0m1to4m5, d0m1to6m7, d0m1to8m9, d0m1to10m11, | ||
179 | d1m0to3m2, d1m0to5m4, d1m0to7m6, d1m0to9m8, d1m0to11m10, | ||
180 | /* Scan mid to channel max123{6-9} only */ | ||
181 | s2to3, s6to7, s6to8, s6to9, s6to10, s6to11, | ||
182 | /* Differential scan mid to channel */ | ||
183 | s6m7to8m9, s6m7to10m11, s7m6to9m8, s7m6to11m10, | ||
184 | }; | ||
185 | |||
186 | /** | ||
187 | * struct max1363_chip_info - chip specifc information | ||
188 | * @name: indentification string for chip | ||
189 | * @num_inputs: number of physical inputs on chip | ||
190 | * @int_vref_mv: the internal reference voltage | ||
191 | * @monitor_mode: whether the chip supports monitor interrupts | ||
192 | * @mode_list: array of available scan modes | ||
193 | * @num_modes: the number of scan modes available | ||
194 | * @default_mode: the scan mode in which the chip starts up | ||
195 | */ | ||
196 | struct max1363_chip_info { | ||
197 | const char *name; | ||
198 | u8 num_inputs; | ||
199 | u16 int_vref_mv; | ||
200 | bool monitor_mode; | ||
201 | const enum max1363_modes *mode_list; | ||
202 | int num_modes; | ||
203 | enum max1363_modes default_mode; | ||
204 | }; | ||
205 | |||
206 | |||
207 | /** | ||
208 | * struct max1363_state - driver instance specific data | ||
209 | * @indio_dev: the industrial I/O device | ||
210 | * @client: i2c_client | ||
211 | * @setupbyte: cache of current device setup byte | ||
212 | * @configbyte: cache of current device config byte | ||
213 | * @chip_info: chip model specific constants, available modes etc | ||
214 | * @current_mode: the scan mode of this chip | ||
215 | * @poll_work: bottom half of polling interrupt handler | ||
216 | * @protect_ring: used to ensure only one polling bh running at a time | ||
217 | * @reg: supply regulator | ||
218 | */ | ||
219 | struct max1363_state { | ||
220 | struct iio_dev *indio_dev; | ||
221 | struct i2c_client *client; | ||
222 | char setupbyte; | ||
223 | char configbyte; | ||
224 | const struct max1363_chip_info *chip_info; | ||
225 | const struct max1363_mode *current_mode; | ||
226 | struct work_struct poll_work; | ||
227 | atomic_t protect_ring; | ||
228 | struct iio_trigger *trig; | ||
229 | struct regulator *reg; | ||
230 | }; | ||
231 | |||
232 | static inline void max1363_uninitialize_ring(struct iio_ring_buffer *ring) | ||
233 | { | ||
234 | }; | ||
235 | |||
236 | static inline int max1363_initialize_ring(struct iio_ring_buffer *ring) | ||
237 | { | ||
238 | return 0; | ||
239 | }; | ||
240 | |||
241 | |||
242 | static inline ssize_t max1363_scan_from_ring(struct device *dev, | ||
243 | struct device_attribute *attr, | ||
244 | char *buf) | ||
245 | { | ||
246 | return 0; | ||
247 | }; | ||
248 | |||
249 | static inline int | ||
250 | max1363_register_ring_funcs_and_init(struct iio_dev *indio_dev) | ||
251 | { | ||
252 | return 0; | ||
253 | }; | ||
254 | |||
255 | static inline void max1363_ring_cleanup(struct iio_dev *indio_dev) {}; | ||
256 | |||
257 | #endif /* _MAX1363_H_ */ | ||
diff --git a/drivers/staging/iio/adc/max1363_core.c b/drivers/staging/iio/adc/max1363_core.c new file mode 100644 index 000000000000..9703881cb3f8 --- /dev/null +++ b/drivers/staging/iio/adc/max1363_core.c | |||
@@ -0,0 +1,623 @@ | |||
1 | /* | ||
2 | * linux/drivers/industrialio/adc/max1363.c | ||
3 | * Copyright (C) 2008 Jonathan Cameron | ||
4 | * | ||
5 | * based on linux/drivers/i2c/chips/max123x | ||
6 | * Copyright (C) 2002-2004 Stefan Eletzhofer | ||
7 | * | ||
8 | * based on linux/drivers/acron/char/pcf8583.c | ||
9 | * Copyright (C) 2000 Russell King | ||
10 | * | ||
11 | * This program is free software; you can redistribute it and/or modify | ||
12 | * it under the terms of the GNU General Public License version 2 as | ||
13 | * published by the Free Software Foundation. | ||
14 | * | ||
15 | * max1363.c | ||
16 | * | ||
17 | * Partial support for max1363 and similar chips. | ||
18 | * | ||
19 | * Not currently implemented. | ||
20 | * | ||
21 | * - Monitor interrrupt generation. | ||
22 | * - Control of internal reference. | ||
23 | * - Sysfs scan interface currently assumes unipolar mode. | ||
24 | */ | ||
25 | |||
26 | #include <linux/interrupt.h> | ||
27 | #include <linux/gpio.h> | ||
28 | #include <linux/workqueue.h> | ||
29 | #include <linux/device.h> | ||
30 | #include <linux/kernel.h> | ||
31 | #include <linux/sysfs.h> | ||
32 | #include <linux/list.h> | ||
33 | #include <linux/i2c.h> | ||
34 | #include <linux/rtc.h> | ||
35 | #include <linux/regulator/consumer.h> | ||
36 | |||
37 | #include "../iio.h" | ||
38 | #include "../sysfs.h" | ||
39 | |||
40 | #include "max1363.h" | ||
41 | |||
42 | /* Available scan modes. | ||
43 | * Awkwardly the associated enum is in the header so it is available to | ||
44 | * the ring buffer code. | ||
45 | */ | ||
46 | static const struct max1363_mode max1363_mode_table[] = { | ||
47 | MAX1363_MODE_SINGLE(0), | ||
48 | MAX1363_MODE_SINGLE(1), | ||
49 | MAX1363_MODE_SINGLE(2), | ||
50 | MAX1363_MODE_SINGLE(3), | ||
51 | MAX1363_MODE_SINGLE(4), | ||
52 | MAX1363_MODE_SINGLE(5), | ||
53 | MAX1363_MODE_SINGLE(6), | ||
54 | MAX1363_MODE_SINGLE(7), | ||
55 | MAX1363_MODE_SINGLE(8), | ||
56 | MAX1363_MODE_SINGLE(9), | ||
57 | MAX1363_MODE_SINGLE(10), | ||
58 | MAX1363_MODE_SINGLE(11), | ||
59 | |||
60 | MAX1363_MODE_SINGLE_TIMES_8(0), | ||
61 | MAX1363_MODE_SINGLE_TIMES_8(1), | ||
62 | MAX1363_MODE_SINGLE_TIMES_8(2), | ||
63 | MAX1363_MODE_SINGLE_TIMES_8(3), | ||
64 | MAX1363_MODE_SINGLE_TIMES_8(4), | ||
65 | MAX1363_MODE_SINGLE_TIMES_8(5), | ||
66 | MAX1363_MODE_SINGLE_TIMES_8(6), | ||
67 | MAX1363_MODE_SINGLE_TIMES_8(7), | ||
68 | MAX1363_MODE_SINGLE_TIMES_8(8), | ||
69 | MAX1363_MODE_SINGLE_TIMES_8(9), | ||
70 | MAX1363_MODE_SINGLE_TIMES_8(10), | ||
71 | MAX1363_MODE_SINGLE_TIMES_8(11), | ||
72 | |||
73 | MAX1363_MODE_SCAN_TO_CHANNEL(1), | ||
74 | MAX1363_MODE_SCAN_TO_CHANNEL(2), | ||
75 | MAX1363_MODE_SCAN_TO_CHANNEL(3), | ||
76 | MAX1363_MODE_SCAN_TO_CHANNEL(4), | ||
77 | MAX1363_MODE_SCAN_TO_CHANNEL(5), | ||
78 | MAX1363_MODE_SCAN_TO_CHANNEL(6), | ||
79 | MAX1363_MODE_SCAN_TO_CHANNEL(7), | ||
80 | MAX1363_MODE_SCAN_TO_CHANNEL(8), | ||
81 | MAX1363_MODE_SCAN_TO_CHANNEL(9), | ||
82 | MAX1363_MODE_SCAN_TO_CHANNEL(10), | ||
83 | MAX1363_MODE_SCAN_TO_CHANNEL(11), | ||
84 | |||
85 | MAX1363_MODE_DIFF_SINGLE(0, 1), | ||
86 | MAX1363_MODE_DIFF_SINGLE(2, 3), | ||
87 | MAX1363_MODE_DIFF_SINGLE(4, 5), | ||
88 | MAX1363_MODE_DIFF_SINGLE(6, 7), | ||
89 | MAX1363_MODE_DIFF_SINGLE(8, 9), | ||
90 | MAX1363_MODE_DIFF_SINGLE(10, 11), | ||
91 | MAX1363_MODE_DIFF_SINGLE(1, 0), | ||
92 | MAX1363_MODE_DIFF_SINGLE(3, 2), | ||
93 | MAX1363_MODE_DIFF_SINGLE(5, 4), | ||
94 | MAX1363_MODE_DIFF_SINGLE(7, 6), | ||
95 | MAX1363_MODE_DIFF_SINGLE(9, 8), | ||
96 | MAX1363_MODE_DIFF_SINGLE(11, 10), | ||
97 | |||
98 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(0, 1), | ||
99 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(2, 3), | ||
100 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(4, 5), | ||
101 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(6, 7), | ||
102 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(8, 9), | ||
103 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(10, 11), | ||
104 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(1, 0), | ||
105 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(3, 2), | ||
106 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(5, 4), | ||
107 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(7, 6), | ||
108 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(9, 8), | ||
109 | MAX1363_MODE_DIFF_SINGLE_TIMES_8(11, 10), | ||
110 | |||
111 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(0-1...2-3, 2, 2), | ||
112 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(0-1...4-5, 4, 3), | ||
113 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(0-1...6-7, 6, 4), | ||
114 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(0-1...8-9, 8, 5), | ||
115 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(0-1...10-11, 10, 6), | ||
116 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(1-0...3-2, 3, 2), | ||
117 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(1-0...5-4, 5, 3), | ||
118 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(1-0...7-6, 7, 4), | ||
119 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(1-0...9-8, 9, 5), | ||
120 | MAX1363_MODE_DIFF_SCAN_TO_CHANNEL_NAMED(1-0...11-10, 11, 6), | ||
121 | |||
122 | MAX1236_MODE_SCAN_MID_TO_CHANNEL(2, 3), | ||
123 | MAX1236_MODE_SCAN_MID_TO_CHANNEL(6, 7), | ||
124 | MAX1236_MODE_SCAN_MID_TO_CHANNEL(6, 8), | ||
125 | MAX1236_MODE_SCAN_MID_TO_CHANNEL(6, 9), | ||
126 | MAX1236_MODE_SCAN_MID_TO_CHANNEL(6, 10), | ||
127 | MAX1236_MODE_SCAN_MID_TO_CHANNEL(6, 11), | ||
128 | |||
129 | MAX1236_MODE_DIFF_SCAN_MID_TO_CHANNEL_NAMED(6-7...8-9, 8, 2), | ||
130 | MAX1236_MODE_DIFF_SCAN_MID_TO_CHANNEL_NAMED(6-7...10-11, 10, 3), | ||
131 | MAX1236_MODE_DIFF_SCAN_MID_TO_CHANNEL_NAMED(7-6...9-8, 9, 2), | ||
132 | MAX1236_MODE_DIFF_SCAN_MID_TO_CHANNEL_NAMED(7-6...11-10, 11, 3), | ||
133 | }; | ||
134 | |||
135 | /* Applies to max1363 */ | ||
136 | static const enum max1363_modes max1363_mode_list[] = { | ||
137 | _s0, _s1, _s2, _s3, | ||
138 | se0, se1, se2, se3, | ||
139 | s0to1, s0to2, s0to3, | ||
140 | d0m1, d2m3, d1m0, d3m2, | ||
141 | de0m1, de2m3, de1m0, de3m2, | ||
142 | d0m1to2m3, d1m0to3m2, | ||
143 | }; | ||
144 | |||
145 | /* Appies to max1236, max1237 */ | ||
146 | static const enum max1363_modes max1236_mode_list[] = { | ||
147 | _s0, _s1, _s2, _s3, | ||
148 | se0, se1, se2, se3, | ||
149 | s0to1, s0to2, s0to3, | ||
150 | d0m1, d2m3, d1m0, d3m2, | ||
151 | de0m1, de2m3, de1m0, de3m2, | ||
152 | d0m1to2m3, d1m0to3m2, | ||
153 | s2to3, | ||
154 | }; | ||
155 | |||
156 | /* Applies to max1238, max1239 */ | ||
157 | static const enum max1363_modes max1238_mode_list[] = { | ||
158 | _s0, _s1, _s2, _s3, _s4, _s5, _s6, _s7, _s8, _s9, _s10, _s11, | ||
159 | se0, se1, se2, se3, se4, se5, se6, se7, se8, se9, se10, se11, | ||
160 | s0to1, s0to2, s0to3, s0to4, s0to5, s0to6, | ||
161 | s0to7, s0to8, s0to9, s0to10, s0to11, | ||
162 | d0m1, d2m3, d4m5, d6m7, d8m9, d10m11, | ||
163 | d1m0, d3m2, d5m4, d7m6, d9m8, d11m10, | ||
164 | de0m1, de2m3, de4m5, de6m7, de8m9, de10m11, | ||
165 | de1m0, de3m2, de5m4, de7m6, de9m8, de11m10, | ||
166 | d0m1to2m3, d0m1to4m5, d0m1to6m7, d0m1to8m9, d0m1to10m11, | ||
167 | d1m0to3m2, d1m0to5m4, d1m0to7m6, d1m0to9m8, d1m0to11m10, | ||
168 | s6to7, s6to8, s6to9, s6to10, s6to11, | ||
169 | s6m7to8m9, s6m7to10m11, s7m6to9m8, s7m6to11m10, | ||
170 | }; | ||
171 | |||
172 | |||
173 | enum { max1361, | ||
174 | max1362, | ||
175 | max1363, | ||
176 | max1364, | ||
177 | max1136, | ||
178 | max1137, | ||
179 | max1138, | ||
180 | max1139, | ||
181 | max1236, | ||
182 | max1237, | ||
183 | max1238, | ||
184 | max1239, | ||
185 | }; | ||
186 | |||
187 | /* max1363 and max1368 tested - rest from data sheet */ | ||
188 | static const struct max1363_chip_info max1363_chip_info_tbl[] = { | ||
189 | { | ||
190 | .name = "max1361", | ||
191 | .num_inputs = 4, | ||
192 | .monitor_mode = 1, | ||
193 | .mode_list = max1363_mode_list, | ||
194 | .num_modes = ARRAY_SIZE(max1363_mode_list), | ||
195 | .default_mode = s0to3, | ||
196 | }, { | ||
197 | .name = "max1362", | ||
198 | .num_inputs = 4, | ||
199 | .monitor_mode = 1, | ||
200 | .mode_list = max1363_mode_list, | ||
201 | .num_modes = ARRAY_SIZE(max1363_mode_list), | ||
202 | .default_mode = s0to3, | ||
203 | }, { | ||
204 | .name = "max1363", | ||
205 | .num_inputs = 4, | ||
206 | .monitor_mode = 1, | ||
207 | .mode_list = max1363_mode_list, | ||
208 | .num_modes = ARRAY_SIZE(max1363_mode_list), | ||
209 | .default_mode = s0to3, | ||
210 | }, { | ||
211 | .name = "max1364", | ||
212 | .num_inputs = 4, | ||
213 | .monitor_mode = 1, | ||
214 | .mode_list = max1363_mode_list, | ||
215 | .num_modes = ARRAY_SIZE(max1363_mode_list), | ||
216 | .default_mode = s0to3, | ||
217 | }, { | ||
218 | .name = "max1136", | ||
219 | .num_inputs = 4, | ||
220 | .int_vref_mv = 4096, | ||
221 | .mode_list = max1236_mode_list, | ||
222 | .num_modes = ARRAY_SIZE(max1236_mode_list), | ||
223 | .default_mode = s0to3, | ||
224 | }, { | ||
225 | .name = "max1137", | ||
226 | .num_inputs = 4, | ||
227 | .int_vref_mv = 2048, | ||
228 | .mode_list = max1236_mode_list, | ||
229 | .num_modes = ARRAY_SIZE(max1236_mode_list), | ||
230 | .default_mode = s0to3, | ||
231 | }, { | ||
232 | .name = "max1138", | ||
233 | .num_inputs = 12, | ||
234 | .int_vref_mv = 4096, | ||
235 | .mode_list = max1238_mode_list, | ||
236 | .num_modes = ARRAY_SIZE(max1238_mode_list), | ||
237 | .default_mode = s0to11, | ||
238 | }, { | ||
239 | .name = "max1139", | ||
240 | .num_inputs = 12, | ||
241 | .int_vref_mv = 2048, | ||
242 | .mode_list = max1238_mode_list, | ||
243 | .num_modes = ARRAY_SIZE(max1238_mode_list), | ||
244 | .default_mode = s0to11, | ||
245 | }, { | ||
246 | .name = "max1236", | ||
247 | .num_inputs = 4, | ||
248 | .int_vref_mv = 4096, | ||
249 | .mode_list = max1236_mode_list, | ||
250 | .num_modes = ARRAY_SIZE(max1236_mode_list), | ||
251 | .default_mode = s0to3, | ||
252 | }, { | ||
253 | .name = "max1237", | ||
254 | .num_inputs = 4, | ||
255 | .int_vref_mv = 2048, | ||
256 | .mode_list = max1236_mode_list, | ||
257 | .num_modes = ARRAY_SIZE(max1236_mode_list), | ||
258 | .default_mode = s0to3, | ||
259 | }, { | ||
260 | .name = "max1238", | ||
261 | .num_inputs = 12, | ||
262 | .int_vref_mv = 4096, | ||
263 | .mode_list = max1238_mode_list, | ||
264 | .num_modes = ARRAY_SIZE(max1238_mode_list), | ||
265 | .default_mode = s0to11, | ||
266 | }, { | ||
267 | .name = "max1239", | ||
268 | .num_inputs = 12, | ||
269 | .int_vref_mv = 2048, | ||
270 | .mode_list = max1238_mode_list, | ||
271 | .num_modes = ARRAY_SIZE(max1238_mode_list), | ||
272 | .default_mode = s0to11, | ||
273 | }, | ||
274 | }; | ||
275 | |||
276 | static int max1363_write_basic_config(struct i2c_client *client, | ||
277 | unsigned char d1, | ||
278 | unsigned char d2) | ||
279 | { | ||
280 | int ret; | ||
281 | u8 *tx_buf = kmalloc(2 , GFP_KERNEL); | ||
282 | if (!tx_buf) | ||
283 | return -ENOMEM; | ||
284 | tx_buf[0] = d1; | ||
285 | tx_buf[1] = d2; | ||
286 | |||
287 | ret = i2c_master_send(client, tx_buf, 2); | ||
288 | kfree(tx_buf); | ||
289 | return (ret > 0) ? 0 : ret; | ||
290 | } | ||
291 | |||
292 | static int max1363_set_scan_mode(struct max1363_state *st) | ||
293 | { | ||
294 | st->configbyte &= ~(MAX1363_CHANNEL_SEL_MASK | ||
295 | | MAX1363_SCAN_MASK | ||
296 | | MAX1363_SE_DE_MASK); | ||
297 | st->configbyte |= st->current_mode->conf; | ||
298 | |||
299 | return max1363_write_basic_config(st->client, | ||
300 | st->setupbyte, | ||
301 | st->configbyte); | ||
302 | } | ||
303 | |||
304 | static int max1363_initial_setup(struct max1363_state *st) | ||
305 | { | ||
306 | st->setupbyte = MAX1363_SETUP_AIN3_IS_AIN3_REF_IS_VDD | ||
307 | | MAX1363_SETUP_POWER_UP_INT_REF | ||
308 | | MAX1363_SETUP_INT_CLOCK | ||
309 | | MAX1363_SETUP_UNIPOLAR | ||
310 | | MAX1363_SETUP_NORESET; | ||
311 | |||
312 | /* Set scan mode writes the config anyway so wait until then*/ | ||
313 | st->setupbyte = MAX1363_SETUP_BYTE(st->setupbyte); | ||
314 | st->current_mode = &max1363_mode_table[st->chip_info->default_mode]; | ||
315 | st->configbyte = MAX1363_CONFIG_BYTE(st->configbyte); | ||
316 | |||
317 | return max1363_set_scan_mode(st); | ||
318 | } | ||
319 | |||
320 | static ssize_t max1363_show_av_scan_modes(struct device *dev, | ||
321 | struct device_attribute *attr, | ||
322 | char *buf) | ||
323 | { | ||
324 | struct iio_dev *dev_info = dev_get_drvdata(dev); | ||
325 | struct max1363_state *st = dev_info->dev_data; | ||
326 | int i, len = 0; | ||
327 | |||
328 | for (i = 0; i < st->chip_info->num_modes; i++) | ||
329 | len += sprintf(buf + len, "%s ", | ||
330 | max1363_mode_table[st->chip_info | ||
331 | ->mode_list[i]].name); | ||
332 | len += sprintf(buf + len, "\n"); | ||
333 | |||
334 | return len; | ||
335 | } | ||
336 | |||
337 | |||
338 | /* The dev here is the sysfs related one, not the underlying i2c one */ | ||
339 | static ssize_t max1363_scan_direct(struct device *dev, | ||
340 | struct device_attribute *attr, | ||
341 | char *buf) | ||
342 | { | ||
343 | struct iio_dev *dev_info = dev_get_drvdata(dev); | ||
344 | struct max1363_state *st = dev_info->dev_data; | ||
345 | int len = 0, ret, i; | ||
346 | struct i2c_client *client = st->client; | ||
347 | char *rxbuf; | ||
348 | |||
349 | if (st->current_mode->numvals == 0) | ||
350 | return 0; | ||
351 | rxbuf = kmalloc(st->current_mode->numvals*2, GFP_KERNEL); | ||
352 | if (rxbuf == NULL) | ||
353 | return -ENOMEM; | ||
354 | |||
355 | /* Interpretation depends on whether these are signed or not!*/ | ||
356 | /* Assume not for now */ | ||
357 | ret = i2c_master_recv(client, rxbuf, st->current_mode->numvals*2); | ||
358 | |||
359 | if (ret < 0) | ||
360 | return ret; | ||
361 | for (i = 0; i < st->current_mode->numvals; i++) | ||
362 | len += sprintf(buf+len, "%d ", | ||
363 | ((int)(rxbuf[i*2+0]&0x0F) << 8) | ||
364 | + ((int)(rxbuf[i*2+1]))); | ||
365 | kfree(rxbuf); | ||
366 | len += sprintf(buf + len, "\n"); | ||
367 | |||
368 | return len; | ||
369 | } | ||
370 | |||
371 | static ssize_t max1363_scan(struct device *dev, | ||
372 | struct device_attribute *attr, | ||
373 | char *buf) | ||
374 | { | ||
375 | struct iio_dev *dev_info = dev_get_drvdata(dev); | ||
376 | int ret; | ||
377 | |||
378 | mutex_lock(&dev_info->mlock); | ||
379 | if (dev_info->currentmode == INDIO_RING_TRIGGERED) | ||
380 | ret = max1363_scan_from_ring(dev, attr, buf); | ||
381 | else | ||
382 | ret = max1363_scan_direct(dev, attr, buf); | ||
383 | mutex_unlock(&dev_info->mlock); | ||
384 | |||
385 | return ret; | ||
386 | } | ||
387 | |||
388 | /* Cannot query the device, so use local copy of state */ | ||
389 | static ssize_t max1363_show_scan_mode(struct device *dev, | ||
390 | struct device_attribute *attr, | ||
391 | char *buf) | ||
392 | { | ||
393 | struct iio_dev *dev_info = dev_get_drvdata(dev); | ||
394 | struct max1363_state *st = dev_info->dev_data; | ||
395 | |||
396 | return sprintf(buf, "%s\n", st->current_mode->name); | ||
397 | } | ||
398 | |||
399 | static const struct max1363_mode | ||
400 | *__max1363_find_mode_in_ci(const struct max1363_chip_info *info, | ||
401 | const char *buf) | ||
402 | { | ||
403 | int i; | ||
404 | for (i = 0; i < info->num_modes; i++) | ||
405 | if (strcmp(max1363_mode_table[info->mode_list[i]].name, buf) | ||
406 | == 0) | ||
407 | return &max1363_mode_table[info->mode_list[i]]; | ||
408 | return NULL; | ||
409 | } | ||
410 | |||
411 | static ssize_t max1363_store_scan_mode(struct device *dev, | ||
412 | struct device_attribute *attr, | ||
413 | const char *buf, | ||
414 | size_t len) | ||
415 | { | ||
416 | struct iio_dev *dev_info = dev_get_drvdata(dev); | ||
417 | struct max1363_state *st = dev_info->dev_data; | ||
418 | const struct max1363_mode *new_mode; | ||
419 | int ret; | ||
420 | |||
421 | mutex_lock(&dev_info->mlock); | ||
422 | new_mode = NULL; | ||
423 | /* Avoid state changes if a ring buffer is enabled */ | ||
424 | if (!iio_ring_enabled(dev_info)) { | ||
425 | new_mode | ||
426 | = __max1363_find_mode_in_ci(st->chip_info, buf); | ||
427 | if (!new_mode) { | ||
428 | ret = -EINVAL; | ||
429 | goto error_ret; | ||
430 | } | ||
431 | st->current_mode = new_mode; | ||
432 | ret = max1363_set_scan_mode(st); | ||
433 | if (ret) | ||
434 | goto error_ret; | ||
435 | } else { | ||
436 | ret = -EBUSY; | ||
437 | goto error_ret; | ||
438 | } | ||
439 | mutex_unlock(&dev_info->mlock); | ||
440 | |||
441 | return len; | ||
442 | |||
443 | error_ret: | ||
444 | mutex_unlock(&dev_info->mlock); | ||
445 | |||
446 | return ret; | ||
447 | } | ||
448 | |||
449 | IIO_DEV_ATTR_AVAIL_SCAN_MODES(max1363_show_av_scan_modes); | ||
450 | IIO_DEV_ATTR_SCAN_MODE(S_IRUGO | S_IWUSR, | ||
451 | max1363_show_scan_mode, | ||
452 | max1363_store_scan_mode); | ||
453 | |||
454 | IIO_DEV_ATTR_SCAN(max1363_scan); | ||
455 | |||
456 | static ssize_t max1363_show_name(struct device *dev, | ||
457 | struct device_attribute *attr, | ||
458 | char *buf) | ||
459 | { | ||
460 | struct iio_dev *dev_info = dev_get_drvdata(dev); | ||
461 | struct max1363_state *st = dev_info->dev_data; | ||
462 | return sprintf(buf, "%s\n", st->chip_info->name); | ||
463 | } | ||
464 | |||
465 | IIO_DEVICE_ATTR(name, S_IRUGO, max1363_show_name, NULL, 0); | ||
466 | |||
467 | /*name export */ | ||
468 | |||
469 | static struct attribute *max1363_attributes[] = { | ||
470 | &iio_dev_attr_available_scan_modes.dev_attr.attr, | ||
471 | &iio_dev_attr_scan_mode.dev_attr.attr, | ||
472 | &iio_dev_attr_scan.dev_attr.attr, | ||
473 | &iio_dev_attr_name.dev_attr.attr, | ||
474 | NULL, | ||
475 | }; | ||
476 | |||
477 | static const struct attribute_group max1363_attribute_group = { | ||
478 | .attrs = max1363_attributes, | ||
479 | }; | ||
480 | |||
481 | static int __devinit max1363_probe(struct i2c_client *client, | ||
482 | const struct i2c_device_id *id) | ||
483 | { | ||
484 | int ret, i, regdone = 0; | ||
485 | struct max1363_state *st = kzalloc(sizeof(*st), GFP_KERNEL); | ||
486 | if (st == NULL) { | ||
487 | ret = -ENOMEM; | ||
488 | goto error_ret; | ||
489 | } | ||
490 | |||
491 | /* this is only used for device removal purposes */ | ||
492 | i2c_set_clientdata(client, st); | ||
493 | |||
494 | atomic_set(&st->protect_ring, 0); | ||
495 | |||
496 | /* Find the chip model specific data */ | ||
497 | for (i = 0; i < ARRAY_SIZE(max1363_chip_info_tbl); i++) | ||
498 | if (!strcmp(max1363_chip_info_tbl[i].name, id->name)) { | ||
499 | st->chip_info = &max1363_chip_info_tbl[i]; | ||
500 | break; | ||
501 | }; | ||
502 | /* Unsupported chip */ | ||
503 | if (!st->chip_info) { | ||
504 | dev_err(&client->dev, "%s is not supported\n", id->name); | ||
505 | ret = -ENODEV; | ||
506 | goto error_free_st; | ||
507 | } | ||
508 | st->reg = regulator_get(&client->dev, "vcc"); | ||
509 | if (!IS_ERR(st->reg)) { | ||
510 | ret = regulator_enable(st->reg); | ||
511 | if (ret) | ||
512 | goto error_put_reg; | ||
513 | } | ||
514 | st->client = client; | ||
515 | |||
516 | st->indio_dev = iio_allocate_device(); | ||
517 | if (st->indio_dev == NULL) { | ||
518 | ret = -ENOMEM; | ||
519 | goto error_disable_reg; | ||
520 | } | ||
521 | |||
522 | /* Estabilish that the iio_dev is a child of the i2c device */ | ||
523 | st->indio_dev->dev.parent = &client->dev; | ||
524 | st->indio_dev->attrs = &max1363_attribute_group; | ||
525 | st->indio_dev->dev_data = (void *)(st); | ||
526 | st->indio_dev->driver_module = THIS_MODULE; | ||
527 | st->indio_dev->modes = INDIO_DIRECT_MODE; | ||
528 | |||
529 | ret = max1363_initial_setup(st); | ||
530 | if (ret) | ||
531 | goto error_free_device; | ||
532 | |||
533 | ret = max1363_register_ring_funcs_and_init(st->indio_dev); | ||
534 | if (ret) | ||
535 | goto error_free_device; | ||
536 | |||
537 | ret = iio_device_register(st->indio_dev); | ||
538 | if (ret) | ||
539 | goto error_cleanup_ring; | ||
540 | regdone = 1; | ||
541 | ret = max1363_initialize_ring(st->indio_dev->ring); | ||
542 | if (ret) | ||
543 | goto error_cleanup_ring; | ||
544 | return 0; | ||
545 | error_cleanup_ring: | ||
546 | max1363_ring_cleanup(st->indio_dev); | ||
547 | error_free_device: | ||
548 | if (!regdone) | ||
549 | iio_free_device(st->indio_dev); | ||
550 | else | ||
551 | iio_device_unregister(st->indio_dev); | ||
552 | error_disable_reg: | ||
553 | if (!IS_ERR(st->reg)) | ||
554 | regulator_disable(st->reg); | ||
555 | error_put_reg: | ||
556 | if (!IS_ERR(st->reg)) | ||
557 | regulator_put(st->reg); | ||
558 | error_free_st: | ||
559 | kfree(st); | ||
560 | |||
561 | error_ret: | ||
562 | return ret; | ||
563 | } | ||
564 | |||
565 | static int max1363_remove(struct i2c_client *client) | ||
566 | { | ||
567 | struct max1363_state *st = i2c_get_clientdata(client); | ||
568 | struct iio_dev *indio_dev = st->indio_dev; | ||
569 | max1363_uninitialize_ring(indio_dev->ring); | ||
570 | max1363_ring_cleanup(indio_dev); | ||
571 | iio_device_unregister(indio_dev); | ||
572 | if (!IS_ERR(st->reg)) { | ||
573 | regulator_disable(st->reg); | ||
574 | regulator_put(st->reg); | ||
575 | } | ||
576 | kfree(st); | ||
577 | |||
578 | return 0; | ||
579 | } | ||
580 | |||
581 | static const struct i2c_device_id max1363_id[] = { | ||
582 | { "max1361", max1361 }, | ||
583 | { "max1362", max1362 }, | ||
584 | { "max1363", max1363 }, | ||
585 | { "max1364", max1364 }, | ||
586 | { "max1136", max1136 }, | ||
587 | { "max1137", max1137 }, | ||
588 | { "max1138", max1138 }, | ||
589 | { "max1139", max1139 }, | ||
590 | { "max1236", max1236 }, | ||
591 | { "max1237", max1237 }, | ||
592 | { "max1238", max1238 }, | ||
593 | { "max1239", max1239 }, | ||
594 | {} | ||
595 | }; | ||
596 | |||
597 | MODULE_DEVICE_TABLE(i2c, max1363_id); | ||
598 | |||
599 | static struct i2c_driver max1363_driver = { | ||
600 | .driver = { | ||
601 | .name = "max1363", | ||
602 | }, | ||
603 | .probe = max1363_probe, | ||
604 | .remove = max1363_remove, | ||
605 | .id_table = max1363_id, | ||
606 | }; | ||
607 | |||
608 | static __init int max1363_init(void) | ||
609 | { | ||
610 | return i2c_add_driver(&max1363_driver); | ||
611 | } | ||
612 | |||
613 | static __exit void max1363_exit(void) | ||
614 | { | ||
615 | i2c_del_driver(&max1363_driver); | ||
616 | } | ||
617 | |||
618 | MODULE_AUTHOR("Jonathan Cameron <jic23@cam.ac.uk>"); | ||
619 | MODULE_DESCRIPTION("Maxim 1363 ADC"); | ||
620 | MODULE_LICENSE("GPL v2"); | ||
621 | |||
622 | module_init(max1363_init); | ||
623 | module_exit(max1363_exit); | ||