]>
Commit | Line | Data |
---|---|---|
d4591719 GKH |
1 | From be8e89087ec2d2c8a1ad1e3db64bf4efdfc3c298 Mon Sep 17 00:00:00 2001 |
2 | From: Ian Abbott <abbotti@mev.co.uk> | |
3 | Date: Mon, 19 Jan 2015 14:47:27 +0000 | |
4 | Subject: staging: comedi: cb_pcidas64: fix incorrect AI range code handling | |
5 | ||
6 | From: Ian Abbott <abbotti@mev.co.uk> | |
7 | ||
8 | commit be8e89087ec2d2c8a1ad1e3db64bf4efdfc3c298 upstream. | |
9 | ||
10 | The hardware range code values and list of valid ranges for the AI | |
11 | subdevice is incorrect for several supported boards. The hardware range | |
12 | code values for all boards except PCI-DAS4020/12 is determined by | |
13 | calling `ai_range_bits_6xxx()` based on the maximum voltage of the range | |
14 | and whether it is bipolar or unipolar, however it only returns the | |
15 | correct hardware range code for the PCI-DAS60xx boards. For | |
16 | PCI-DAS6402/16 (and /12) it returns the wrong code for the unipolar | |
17 | ranges. For PCI-DAS64/Mx/16 it returns the wrong code for all the | |
18 | ranges and the comedi range table is incorrect. | |
19 | ||
20 | Change `ai_range_bits_6xxx()` to use a look-up table pointed to by new | |
21 | member `ai_range_codes` of `struct pcidas64_board` to map the comedi | |
22 | range table indices to the hardware range codes. Use a new comedi range | |
23 | table for the PCI-DAS64/Mx/16 boards (and the commented out variants). | |
24 | ||
25 | Signed-off-by: Ian Abbott <abbotti@mev.co.uk> | |
26 | Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> | |
27 | ||
28 | --- | |
29 | drivers/staging/comedi/drivers/cb_pcidas64.c | 124 ++++++++++++++++----------- | |
30 | 1 file changed, 76 insertions(+), 48 deletions(-) | |
31 | ||
32 | --- a/drivers/staging/comedi/drivers/cb_pcidas64.c | |
33 | +++ b/drivers/staging/comedi/drivers/cb_pcidas64.c | |
34 | @@ -455,6 +455,29 @@ static const struct comedi_lrange ai_ran | |
35 | } | |
36 | }; | |
37 | ||
38 | +static const uint8_t ai_range_code_64xx[8] = { | |
39 | + 0x0, 0x1, 0x2, 0x3, /* bipolar 10, 5, 2,5, 1.25 */ | |
40 | + 0x8, 0x9, 0xa, 0xb /* unipolar 10, 5, 2.5, 1.25 */ | |
41 | +}; | |
42 | + | |
43 | +/* analog input ranges for 64-Mx boards */ | |
44 | +static const struct comedi_lrange ai_ranges_64_mx = { | |
45 | + 7, { | |
46 | + BIP_RANGE(5), | |
47 | + BIP_RANGE(2.5), | |
48 | + BIP_RANGE(1.25), | |
49 | + BIP_RANGE(0.625), | |
50 | + UNI_RANGE(5), | |
51 | + UNI_RANGE(2.5), | |
52 | + UNI_RANGE(1.25) | |
53 | + } | |
54 | +}; | |
55 | + | |
56 | +static const uint8_t ai_range_code_64_mx[7] = { | |
57 | + 0x0, 0x1, 0x2, 0x3, /* bipolar 5, 2.5, 1.25, 0.625 */ | |
58 | + 0x9, 0xa, 0xb /* unipolar 5, 2.5, 1.25 */ | |
59 | +}; | |
60 | + | |
61 | /* analog input ranges for 60xx boards */ | |
62 | static const struct comedi_lrange ai_ranges_60xx = { | |
63 | 4, | |
64 | @@ -466,6 +489,10 @@ static const struct comedi_lrange ai_ran | |
65 | } | |
66 | }; | |
67 | ||
68 | +static const uint8_t ai_range_code_60xx[4] = { | |
69 | + 0x0, 0x1, 0x4, 0x7 /* bipolar 10, 5, 0.5, 0.05 */ | |
70 | +}; | |
71 | + | |
72 | /* analog input ranges for 6030, etc boards */ | |
73 | static const struct comedi_lrange ai_ranges_6030 = { | |
74 | 14, | |
75 | @@ -487,6 +514,11 @@ static const struct comedi_lrange ai_ran | |
76 | } | |
77 | }; | |
78 | ||
79 | +static const uint8_t ai_range_code_6030[14] = { | |
80 | + 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, /* bip 10, 5, 2, 1, 0.5, 0.2, 0.1 */ | |
81 | + 0x9, 0xa, 0xb, 0xc, 0xd, 0xe, 0xf /* uni 10, 5, 2, 1, 0.5, 0.2, 0.1 */ | |
82 | +}; | |
83 | + | |
84 | /* analog input ranges for 6052, etc boards */ | |
85 | static const struct comedi_lrange ai_ranges_6052 = { | |
86 | 15, | |
87 | @@ -509,6 +541,11 @@ static const struct comedi_lrange ai_ran | |
88 | } | |
89 | }; | |
90 | ||
91 | +static const uint8_t ai_range_code_6052[15] = { | |
92 | + 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, /* bipolar 10 ... 0.05 */ | |
93 | + 0x9, 0xa, 0xb, 0xc, 0xd, 0xe, 0xf /* unipolar 10 ... 0.1 */ | |
94 | +}; | |
95 | + | |
96 | /* analog input ranges for 4020 board */ | |
97 | static const struct comedi_lrange ai_ranges_4020 = { | |
98 | 2, | |
99 | @@ -616,6 +653,7 @@ struct pcidas64_board { | |
100 | int ai_bits; /* analog input resolution */ | |
101 | int ai_speed; /* fastest conversion period in ns */ | |
102 | const struct comedi_lrange *ai_range_table; | |
103 | + const uint8_t *ai_range_code; | |
104 | int ao_nchan; /* number of analog out channels */ | |
105 | int ao_bits; /* analog output resolution */ | |
106 | int ao_scan_speed; /* analog output scan speed */ | |
107 | @@ -674,6 +712,7 @@ static const struct pcidas64_board pcida | |
108 | .ao_scan_speed = 10000, | |
109 | .layout = LAYOUT_64XX, | |
110 | .ai_range_table = &ai_ranges_64xx, | |
111 | + .ai_range_code = ai_range_code_64xx, | |
112 | .ao_range_table = &ao_ranges_64xx, | |
113 | .ao_range_code = ao_range_code_64xx, | |
114 | .ai_fifo = &ai_fifo_64xx, | |
115 | @@ -689,6 +728,7 @@ static const struct pcidas64_board pcida | |
116 | .ao_scan_speed = 10000, | |
117 | .layout = LAYOUT_64XX, | |
118 | .ai_range_table = &ai_ranges_64xx, | |
119 | + .ai_range_code = ai_range_code_64xx, | |
120 | .ao_range_table = &ao_ranges_64xx, | |
121 | .ao_range_code = ao_range_code_64xx, | |
122 | .ai_fifo = &ai_fifo_64xx, | |
123 | @@ -703,7 +743,8 @@ static const struct pcidas64_board pcida | |
124 | .ao_bits = 16, | |
125 | .ao_scan_speed = 10000, | |
126 | .layout = LAYOUT_64XX, | |
127 | - .ai_range_table = &ai_ranges_64xx, | |
128 | + .ai_range_table = &ai_ranges_64_mx, | |
129 | + .ai_range_code = ai_range_code_64_mx, | |
130 | .ao_range_table = &ao_ranges_64xx, | |
131 | .ao_range_code = ao_range_code_64xx, | |
132 | .ai_fifo = &ai_fifo_64xx, | |
133 | @@ -718,7 +759,8 @@ static const struct pcidas64_board pcida | |
134 | .ao_bits = 16, | |
135 | .ao_scan_speed = 10000, | |
136 | .layout = LAYOUT_64XX, | |
137 | - .ai_range_table = &ai_ranges_64xx, | |
138 | + .ai_range_table = &ai_ranges_64_mx, | |
139 | + .ai_range_code = ai_range_code_64_mx, | |
140 | .ao_range_table = &ao_ranges_64xx, | |
141 | .ao_range_code = ao_range_code_64xx, | |
142 | .ai_fifo = &ai_fifo_64xx, | |
143 | @@ -733,7 +775,8 @@ static const struct pcidas64_board pcida | |
144 | .ao_bits = 16, | |
145 | .ao_scan_speed = 10000, | |
146 | .layout = LAYOUT_64XX, | |
147 | - .ai_range_table = &ai_ranges_64xx, | |
148 | + .ai_range_table = &ai_ranges_64_mx, | |
149 | + .ai_range_code = ai_range_code_64_mx, | |
150 | .ao_range_table = &ao_ranges_64xx, | |
151 | .ao_range_code = ao_range_code_64xx, | |
152 | .ai_fifo = &ai_fifo_64xx, | |
153 | @@ -748,6 +791,7 @@ static const struct pcidas64_board pcida | |
154 | .ao_bits = 16, | |
155 | .layout = LAYOUT_60XX, | |
156 | .ai_range_table = &ai_ranges_60xx, | |
157 | + .ai_range_code = ai_range_code_60xx, | |
158 | .ao_range_table = &range_bipolar10, | |
159 | .ao_range_code = ao_range_code_60xx, | |
160 | .ai_fifo = &ai_fifo_60xx, | |
161 | @@ -763,6 +807,7 @@ static const struct pcidas64_board pcida | |
162 | .ao_scan_speed = 100000, | |
163 | .layout = LAYOUT_60XX, | |
164 | .ai_range_table = &ai_ranges_60xx, | |
165 | + .ai_range_code = ai_range_code_60xx, | |
166 | .ao_range_table = &range_bipolar10, | |
167 | .ao_range_code = ao_range_code_60xx, | |
168 | .ai_fifo = &ai_fifo_60xx, | |
169 | @@ -777,6 +822,7 @@ static const struct pcidas64_board pcida | |
170 | .ao_scan_speed = 100000, | |
171 | .layout = LAYOUT_60XX, | |
172 | .ai_range_table = &ai_ranges_60xx, | |
173 | + .ai_range_code = ai_range_code_60xx, | |
174 | .ao_range_table = &range_bipolar10, | |
175 | .ao_range_code = ao_range_code_60xx, | |
176 | .ai_fifo = &ai_fifo_60xx, | |
177 | @@ -792,6 +838,7 @@ static const struct pcidas64_board pcida | |
178 | .ao_scan_speed = 100000, | |
179 | .layout = LAYOUT_60XX, | |
180 | .ai_range_table = &ai_ranges_60xx, | |
181 | + .ai_range_code = ai_range_code_60xx, | |
182 | .ao_range_table = &range_bipolar10, | |
183 | .ao_range_code = ao_range_code_60xx, | |
184 | .ai_fifo = &ai_fifo_60xx, | |
185 | @@ -807,6 +854,7 @@ static const struct pcidas64_board pcida | |
186 | .ao_scan_speed = 10000, | |
187 | .layout = LAYOUT_60XX, | |
188 | .ai_range_table = &ai_ranges_6030, | |
189 | + .ai_range_code = ai_range_code_6030, | |
190 | .ao_range_table = &ao_ranges_6030, | |
191 | .ao_range_code = ao_range_code_6030, | |
192 | .ai_fifo = &ai_fifo_60xx, | |
193 | @@ -822,6 +870,7 @@ static const struct pcidas64_board pcida | |
194 | .ao_scan_speed = 10000, | |
195 | .layout = LAYOUT_60XX, | |
196 | .ai_range_table = &ai_ranges_6030, | |
197 | + .ai_range_code = ai_range_code_6030, | |
198 | .ao_range_table = &ao_ranges_6030, | |
199 | .ao_range_code = ao_range_code_6030, | |
200 | .ai_fifo = &ai_fifo_60xx, | |
201 | @@ -835,6 +884,7 @@ static const struct pcidas64_board pcida | |
202 | .ao_nchan = 0, | |
203 | .layout = LAYOUT_60XX, | |
204 | .ai_range_table = &ai_ranges_6030, | |
205 | + .ai_range_code = ai_range_code_6030, | |
206 | .ai_fifo = &ai_fifo_60xx, | |
207 | .has_8255 = 0, | |
208 | }, | |
209 | @@ -846,6 +896,7 @@ static const struct pcidas64_board pcida | |
210 | .ao_nchan = 0, | |
211 | .layout = LAYOUT_60XX, | |
212 | .ai_range_table = &ai_ranges_6030, | |
213 | + .ai_range_code = ai_range_code_6030, | |
214 | .ai_fifo = &ai_fifo_60xx, | |
215 | .has_8255 = 0, | |
216 | }, | |
217 | @@ -858,6 +909,7 @@ static const struct pcidas64_board pcida | |
218 | .ao_scan_speed = 0, | |
219 | .layout = LAYOUT_60XX, | |
220 | .ai_range_table = &ai_ranges_60xx, | |
221 | + .ai_range_code = ai_range_code_60xx, | |
222 | .ai_fifo = &ai_fifo_60xx, | |
223 | .has_8255 = 0, | |
224 | }, | |
225 | @@ -871,6 +923,7 @@ static const struct pcidas64_board pcida | |
226 | .ao_scan_speed = 100000, | |
227 | .layout = LAYOUT_60XX, | |
228 | .ai_range_table = &ai_ranges_60xx, | |
229 | + .ai_range_code = ai_range_code_60xx, | |
230 | .ao_range_table = &range_bipolar10, | |
231 | .ao_range_code = ao_range_code_60xx, | |
232 | .ai_fifo = &ai_fifo_60xx, | |
233 | @@ -886,6 +939,7 @@ static const struct pcidas64_board pcida | |
234 | .ao_scan_speed = 100000, | |
235 | .layout = LAYOUT_60XX, | |
236 | .ai_range_table = &ai_ranges_60xx, | |
237 | + .ai_range_code = ai_range_code_60xx, | |
238 | .ao_range_table = &range_bipolar10, | |
239 | .ao_range_code = ao_range_code_60xx, | |
240 | .ai_fifo = &ai_fifo_60xx, | |
241 | @@ -901,6 +955,7 @@ static const struct pcidas64_board pcida | |
242 | .ao_scan_speed = 1000, | |
243 | .layout = LAYOUT_60XX, | |
244 | .ai_range_table = &ai_ranges_6052, | |
245 | + .ai_range_code = ai_range_code_6052, | |
246 | .ao_range_table = &ao_ranges_6030, | |
247 | .ao_range_code = ao_range_code_6030, | |
248 | .ai_fifo = &ai_fifo_60xx, | |
249 | @@ -916,6 +971,7 @@ static const struct pcidas64_board pcida | |
250 | .ao_scan_speed = 3333, | |
251 | .layout = LAYOUT_60XX, | |
252 | .ai_range_table = &ai_ranges_6052, | |
253 | + .ai_range_code = ai_range_code_6052, | |
254 | .ao_range_table = &ao_ranges_6030, | |
255 | .ao_range_code = ao_range_code_6030, | |
256 | .ai_fifo = &ai_fifo_60xx, | |
257 | @@ -931,6 +987,7 @@ static const struct pcidas64_board pcida | |
258 | .ao_scan_speed = 1000, | |
259 | .layout = LAYOUT_60XX, | |
260 | .ai_range_table = &ai_ranges_6052, | |
261 | + .ai_range_code = ai_range_code_6052, | |
262 | .ao_range_table = &ao_ranges_6030, | |
263 | .ao_range_code = ao_range_code_6030, | |
264 | .ai_fifo = &ai_fifo_60xx, | |
265 | @@ -946,6 +1003,7 @@ static const struct pcidas64_board pcida | |
266 | .ao_scan_speed = 1000, | |
267 | .layout = LAYOUT_60XX, | |
268 | .ai_range_table = &ai_ranges_6052, | |
269 | + .ai_range_code = ai_range_code_6052, | |
270 | .ao_range_table = &ao_ranges_6030, | |
271 | .ao_range_code = ao_range_code_6030, | |
272 | .ai_fifo = &ai_fifo_60xx, | |
273 | @@ -980,6 +1038,7 @@ static const struct pcidas64_board pcida | |
274 | .ao_scan_speed = 10000, | |
275 | .layout = LAYOUT_64XX, | |
276 | .ai_range_table = &ai_ranges_64xx, | |
277 | + .ai_range_code = ai_range_code_64xx, | |
278 | .ai_fifo = ai_fifo_64xx, | |
279 | .has_8255 = 1, | |
280 | }, | |
281 | @@ -991,7 +1050,8 @@ static const struct pcidas64_board pcida | |
282 | .ao_nchan = 0, | |
283 | .ao_scan_speed = 10000, | |
284 | .layout = LAYOUT_64XX, | |
285 | - .ai_range_table = &ai_ranges_64xx, | |
286 | + .ai_range_table = &ai_ranges_64_mx, | |
287 | + .ai_range_code = ai_range_code_64_mx, | |
288 | .ai_fifo = ai_fifo_64xx, | |
289 | .has_8255 = 1, | |
290 | }, | |
291 | @@ -1003,7 +1063,8 @@ static const struct pcidas64_board pcida | |
292 | .ao_nchan = 0, | |
293 | .ao_scan_speed = 10000, | |
294 | .layout = LAYOUT_64XX, | |
295 | - .ai_range_table = &ai_ranges_64xx, | |
296 | + .ai_range_table = &ai_ranges_64_mx, | |
297 | + .ai_range_code = ai_range_code_64_mx, | |
298 | .ai_fifo = ai_fifo_64xx, | |
299 | .has_8255 = 1, | |
300 | }, | |
301 | @@ -1015,7 +1076,8 @@ static const struct pcidas64_board pcida | |
302 | .ao_nchan = 0, | |
303 | .ao_scan_speed = 10000, | |
304 | .layout = LAYOUT_64XX, | |
305 | - .ai_range_table = &ai_ranges_64xx, | |
306 | + .ai_range_table = &ai_ranges_64_mx, | |
307 | + .ai_range_code = ai_range_code_64_mx, | |
308 | .ai_fifo = ai_fifo_64xx, | |
309 | .has_8255 = 1, | |
310 | }, | |
311 | @@ -1027,7 +1089,8 @@ static const struct pcidas64_board pcida | |
312 | .ao_nchan = 2, | |
313 | .ao_scan_speed = 10000, | |
314 | .layout = LAYOUT_64XX, | |
315 | - .ai_range_table = &ai_ranges_64xx, | |
316 | + .ai_range_table = &ai_ranges_64_mx, | |
317 | + .ai_range_code = ai_range_code_64_mx, | |
318 | .ai_fifo = ai_fifo_64xx, | |
319 | .has_8255 = 1, | |
320 | }, | |
321 | @@ -1039,7 +1102,8 @@ static const struct pcidas64_board pcida | |
322 | .ao_nchan = 2, | |
323 | .ao_scan_speed = 10000, | |
324 | .layout = LAYOUT_64XX, | |
325 | - .ai_range_table = &ai_ranges_64xx, | |
326 | + .ai_range_table = &ai_ranges_64_mx, | |
327 | + .ai_range_code = ai_range_code_64_mx, | |
328 | .ai_fifo = ai_fifo_64xx, | |
329 | .has_8255 = 1, | |
330 | }, | |
331 | @@ -1051,7 +1115,8 @@ static const struct pcidas64_board pcida | |
332 | .ao_nchan = 2, | |
333 | .ao_scan_speed = 10000, | |
334 | .layout = LAYOUT_64XX, | |
335 | - .ai_range_table = &ai_ranges_64xx, | |
336 | + .ai_range_table = &ai_ranges_64_mx, | |
337 | + .ai_range_code = ai_range_code_64_mx, | |
338 | .ai_fifo = ai_fifo_64xx, | |
339 | .has_8255 = 1, | |
340 | }, | |
341 | @@ -1148,45 +1213,8 @@ static unsigned int ai_range_bits_6xxx(c | |
342 | unsigned int range_index) | |
343 | { | |
344 | const struct pcidas64_board *thisboard = comedi_board(dev); | |
345 | - const struct comedi_krange *range = | |
346 | - &thisboard->ai_range_table->range[range_index]; | |
347 | - unsigned int bits = 0; | |
348 | - | |
349 | - switch (range->max) { | |
350 | - case 10000000: | |
351 | - bits = 0x000; | |
352 | - break; | |
353 | - case 5000000: | |
354 | - bits = 0x100; | |
355 | - break; | |
356 | - case 2000000: | |
357 | - case 2500000: | |
358 | - bits = 0x200; | |
359 | - break; | |
360 | - case 1000000: | |
361 | - case 1250000: | |
362 | - bits = 0x300; | |
363 | - break; | |
364 | - case 500000: | |
365 | - bits = 0x400; | |
366 | - break; | |
367 | - case 200000: | |
368 | - case 250000: | |
369 | - bits = 0x500; | |
370 | - break; | |
371 | - case 100000: | |
372 | - bits = 0x600; | |
373 | - break; | |
374 | - case 50000: | |
375 | - bits = 0x700; | |
376 | - break; | |
377 | - default: | |
378 | - comedi_error(dev, "bug! in ai_range_bits_6xxx"); | |
379 | - break; | |
380 | - } | |
381 | - if (range->min == 0) | |
382 | - bits += 0x900; | |
383 | - return bits; | |
384 | + | |
385 | + return thisboard->ai_range_code[range_index] << 8; | |
386 | } | |
387 | ||
388 | static unsigned int hw_revision(const struct comedi_device *dev, |