Diff markup
1 /* 1 /*
2 * 2 *
3 * $Id$ <<
4 * 3 *
5 * Copyright (C) 2005 Mike Isely <isely@pobox 4 * Copyright (C) 2005 Mike Isely <isely@pobox.com>
6 * 5 *
7 * This program is free software; you can red 6 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Publ 7 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either versi 8 * the Free Software Foundation; either version 2 of the License
10 * 9 *
11 * This program is distributed in the hope th 10 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULA 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more detail 13 * GNU General Public License for more details.
15 * 14 *
16 * You should have received a copy of the GNU 15 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to 16 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 3 17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 * 18 *
20 */ 19 */
21 20
22 #include "pvrusb2-ctrl.h" 21 #include "pvrusb2-ctrl.h"
23 #include "pvrusb2-hdw-internal.h" 22 #include "pvrusb2-hdw-internal.h"
24 #include <linux/errno.h> 23 #include <linux/errno.h>
25 #include <linux/string.h> 24 #include <linux/string.h>
26 #include <linux/mutex.h> 25 #include <linux/mutex.h>
27 26
28 27
29 static int pvr2_ctrl_range_check(struct pvr2_c 28 static int pvr2_ctrl_range_check(struct pvr2_ctrl *cptr,int val)
30 { 29 {
31 if (cptr->info->check_value) { 30 if (cptr->info->check_value) {
32 if (!cptr->info->check_value(c 31 if (!cptr->info->check_value(cptr,val)) return -ERANGE;
>> 32 } else if (cptr->info->type == pvr2_ctl_enum) {
>> 33 if (val < 0) return -ERANGE;
>> 34 if (val >= cptr->info->def.type_enum.count) return -ERANGE;
33 } else { 35 } else {
34 int lim; 36 int lim;
35 lim = cptr->info->def.type_int 37 lim = cptr->info->def.type_int.min_value;
36 if (cptr->info->get_min_value) 38 if (cptr->info->get_min_value) {
37 cptr->info->get_min_va 39 cptr->info->get_min_value(cptr,&lim);
38 } 40 }
39 if (val < lim) return -ERANGE; 41 if (val < lim) return -ERANGE;
40 lim = cptr->info->def.type_int 42 lim = cptr->info->def.type_int.max_value;
41 if (cptr->info->get_max_value) 43 if (cptr->info->get_max_value) {
42 cptr->info->get_max_va 44 cptr->info->get_max_value(cptr,&lim);
43 } 45 }
44 if (val > lim) return -ERANGE; 46 if (val > lim) return -ERANGE;
45 } 47 }
46 return 0; 48 return 0;
47 } 49 }
48 50
49 51
50 /* Set the given control. */ 52 /* Set the given control. */
51 int pvr2_ctrl_set_value(struct pvr2_ctrl *cptr 53 int pvr2_ctrl_set_value(struct pvr2_ctrl *cptr,int val)
52 { 54 {
53 return pvr2_ctrl_set_mask_value(cptr,~ 55 return pvr2_ctrl_set_mask_value(cptr,~0,val);
54 } 56 }
55 57
56 58
57 /* Set/clear specific bits of the given contro 59 /* Set/clear specific bits of the given control. */
58 int pvr2_ctrl_set_mask_value(struct pvr2_ctrl 60 int pvr2_ctrl_set_mask_value(struct pvr2_ctrl *cptr,int mask,int val)
59 { 61 {
60 int ret = 0; 62 int ret = 0;
61 if (!cptr) return -EINVAL; 63 if (!cptr) return -EINVAL;
62 LOCK_TAKE(cptr->hdw->big_lock); do { 64 LOCK_TAKE(cptr->hdw->big_lock); do {
63 if (cptr->info->set_value) { 65 if (cptr->info->set_value) {
64 if (cptr->info->type = 66 if (cptr->info->type == pvr2_ctl_bitmask) {
65 mask &= cptr-> 67 mask &= cptr->info->def.type_bitmask.valid_bits;
66 } else if (cptr->info- !! 68 } else if ((cptr->info->type == pvr2_ctl_int)||
>> 69 (cptr->info->type == pvr2_ctl_enum)) {
67 ret = pvr2_ctr 70 ret = pvr2_ctrl_range_check(cptr,val);
68 if (ret < 0) b 71 if (ret < 0) break;
69 } else if (cptr->info- <<
70 if (val >= cpt <<
71 break; <<
72 } <<
73 } else if (cptr->info- 72 } else if (cptr->info->type != pvr2_ctl_bool) {
74 break; 73 break;
75 } 74 }
76 ret = cptr->info->set_ 75 ret = cptr->info->set_value(cptr,mask,val);
77 } else { 76 } else {
78 ret = -EPERM; 77 ret = -EPERM;
79 } 78 }
80 } while(0); LOCK_GIVE(cptr->hdw->big_l 79 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
81 return ret; 80 return ret;
82 } 81 }
83 82
84 83
85 /* Get the current value of the given control. 84 /* Get the current value of the given control. */
86 int pvr2_ctrl_get_value(struct pvr2_ctrl *cptr 85 int pvr2_ctrl_get_value(struct pvr2_ctrl *cptr,int *valptr)
87 { 86 {
88 int ret = 0; 87 int ret = 0;
89 if (!cptr) return -EINVAL; 88 if (!cptr) return -EINVAL;
90 LOCK_TAKE(cptr->hdw->big_lock); do { 89 LOCK_TAKE(cptr->hdw->big_lock); do {
91 ret = cptr->info->get_value(cp 90 ret = cptr->info->get_value(cptr,valptr);
92 } while(0); LOCK_GIVE(cptr->hdw->big_l 91 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
93 return ret; 92 return ret;
94 } 93 }
95 94
96 95
97 /* Retrieve control's type */ 96 /* Retrieve control's type */
98 enum pvr2_ctl_type pvr2_ctrl_get_type(struct p 97 enum pvr2_ctl_type pvr2_ctrl_get_type(struct pvr2_ctrl *cptr)
99 { 98 {
100 if (!cptr) return pvr2_ctl_int; 99 if (!cptr) return pvr2_ctl_int;
101 return cptr->info->type; 100 return cptr->info->type;
102 } 101 }
103 102
104 103
105 /* Retrieve control's maximum value (int type) 104 /* Retrieve control's maximum value (int type) */
106 int pvr2_ctrl_get_max(struct pvr2_ctrl *cptr) 105 int pvr2_ctrl_get_max(struct pvr2_ctrl *cptr)
107 { 106 {
108 int ret = 0; 107 int ret = 0;
109 if (!cptr) return 0; 108 if (!cptr) return 0;
110 LOCK_TAKE(cptr->hdw->big_lock); do { 109 LOCK_TAKE(cptr->hdw->big_lock); do {
111 if (cptr->info->get_max_value) 110 if (cptr->info->get_max_value) {
112 cptr->info->get_max_va 111 cptr->info->get_max_value(cptr,&ret);
113 } else if (cptr->info->type == 112 } else if (cptr->info->type == pvr2_ctl_int) {
114 ret = cptr->info->def. 113 ret = cptr->info->def.type_int.max_value;
115 } 114 }
116 } while(0); LOCK_GIVE(cptr->hdw->big_l 115 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
117 return ret; 116 return ret;
118 } 117 }
119 118
120 119
121 /* Retrieve control's minimum value (int type) 120 /* Retrieve control's minimum value (int type) */
122 int pvr2_ctrl_get_min(struct pvr2_ctrl *cptr) 121 int pvr2_ctrl_get_min(struct pvr2_ctrl *cptr)
123 { 122 {
124 int ret = 0; 123 int ret = 0;
125 if (!cptr) return 0; 124 if (!cptr) return 0;
126 LOCK_TAKE(cptr->hdw->big_lock); do { 125 LOCK_TAKE(cptr->hdw->big_lock); do {
127 if (cptr->info->get_min_value) 126 if (cptr->info->get_min_value) {
128 cptr->info->get_min_va 127 cptr->info->get_min_value(cptr,&ret);
129 } else if (cptr->info->type == 128 } else if (cptr->info->type == pvr2_ctl_int) {
130 ret = cptr->info->def. 129 ret = cptr->info->def.type_int.min_value;
131 } 130 }
132 } while(0); LOCK_GIVE(cptr->hdw->big_l 131 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
133 return ret; 132 return ret;
134 } 133 }
135 134
136 135
137 /* Retrieve control's default value (any type) 136 /* Retrieve control's default value (any type) */
138 int pvr2_ctrl_get_def(struct pvr2_ctrl *cptr) !! 137 int pvr2_ctrl_get_def(struct pvr2_ctrl *cptr, int *valptr)
139 { 138 {
140 int ret = 0; 139 int ret = 0;
141 if (!cptr) return 0; !! 140 if (!cptr) return -EINVAL;
142 LOCK_TAKE(cptr->hdw->big_lock); do { 141 LOCK_TAKE(cptr->hdw->big_lock); do {
143 if (cptr->info->type == pvr2_c !! 142 if (cptr->info->get_def_value) {
144 ret = cptr->info->defa !! 143 ret = cptr->info->get_def_value(cptr, valptr);
>> 144 } else {
>> 145 *valptr = cptr->info->default_value;
145 } 146 }
146 } while(0); LOCK_GIVE(cptr->hdw->big_l 147 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
147 return ret; 148 return ret;
148 } 149 }
149 150
150 151
151 /* Retrieve control's enumeration count (enum 152 /* Retrieve control's enumeration count (enum only) */
152 int pvr2_ctrl_get_cnt(struct pvr2_ctrl *cptr) 153 int pvr2_ctrl_get_cnt(struct pvr2_ctrl *cptr)
153 { 154 {
154 int ret = 0; 155 int ret = 0;
155 if (!cptr) return 0; 156 if (!cptr) return 0;
156 LOCK_TAKE(cptr->hdw->big_lock); do { 157 LOCK_TAKE(cptr->hdw->big_lock); do {
157 if (cptr->info->type == pvr2_c 158 if (cptr->info->type == pvr2_ctl_enum) {
158 ret = cptr->info->def. 159 ret = cptr->info->def.type_enum.count;
159 } 160 }
160 } while(0); LOCK_GIVE(cptr->hdw->big_l 161 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
161 return ret; 162 return ret;
162 } 163 }
163 164
164 165
165 /* Retrieve control's valid mask bits (bit mas 166 /* Retrieve control's valid mask bits (bit mask only) */
166 int pvr2_ctrl_get_mask(struct pvr2_ctrl *cptr) 167 int pvr2_ctrl_get_mask(struct pvr2_ctrl *cptr)
167 { 168 {
168 int ret = 0; 169 int ret = 0;
169 if (!cptr) return 0; 170 if (!cptr) return 0;
170 LOCK_TAKE(cptr->hdw->big_lock); do { 171 LOCK_TAKE(cptr->hdw->big_lock); do {
171 if (cptr->info->type == pvr2_c 172 if (cptr->info->type == pvr2_ctl_bitmask) {
172 ret = cptr->info->def. 173 ret = cptr->info->def.type_bitmask.valid_bits;
173 } 174 }
174 } while(0); LOCK_GIVE(cptr->hdw->big_l 175 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
175 return ret; 176 return ret;
176 } 177 }
177 178
178 179
179 /* Retrieve the control's name */ 180 /* Retrieve the control's name */
180 const char *pvr2_ctrl_get_name(struct pvr2_ctr 181 const char *pvr2_ctrl_get_name(struct pvr2_ctrl *cptr)
181 { 182 {
182 if (!cptr) return NULL; 183 if (!cptr) return NULL;
183 return cptr->info->name; 184 return cptr->info->name;
184 } 185 }
185 186
186 187
187 /* Retrieve the control's desc */ 188 /* Retrieve the control's desc */
188 const char *pvr2_ctrl_get_desc(struct pvr2_ctr 189 const char *pvr2_ctrl_get_desc(struct pvr2_ctrl *cptr)
189 { 190 {
190 if (!cptr) return NULL; 191 if (!cptr) return NULL;
191 return cptr->info->desc; 192 return cptr->info->desc;
192 } 193 }
193 194
194 195
195 /* Retrieve a control enumeration or bit mask 196 /* Retrieve a control enumeration or bit mask value */
196 int pvr2_ctrl_get_valname(struct pvr2_ctrl *cp 197 int pvr2_ctrl_get_valname(struct pvr2_ctrl *cptr,int val,
197 char *bptr,unsigned 198 char *bptr,unsigned int bmax,
198 unsigned int *blen) 199 unsigned int *blen)
199 { 200 {
200 int ret = -EINVAL; 201 int ret = -EINVAL;
201 if (!cptr) return 0; 202 if (!cptr) return 0;
202 *blen = 0; 203 *blen = 0;
203 LOCK_TAKE(cptr->hdw->big_lock); do { 204 LOCK_TAKE(cptr->hdw->big_lock); do {
204 if (cptr->info->type == pvr2_c 205 if (cptr->info->type == pvr2_ctl_enum) {
205 const char **names; 206 const char **names;
206 names = cptr->info->de 207 names = cptr->info->def.type_enum.value_names;
207 if ((val >= 0) && !! 208 if (pvr2_ctrl_range_check(cptr,val) == 0) {
208 (val < cptr->info- <<
209 if (names[val] 209 if (names[val]) {
210 *blen 210 *blen = scnprintf(
211 211 bptr,bmax,"%s",
212 212 names[val]);
213 } else { 213 } else {
214 *blen 214 *blen = 0;
215 } 215 }
216 ret = 0; 216 ret = 0;
217 } 217 }
218 } else if (cptr->info->type == 218 } else if (cptr->info->type == pvr2_ctl_bitmask) {
219 const char **names; 219 const char **names;
220 unsigned int idx; 220 unsigned int idx;
221 int msk; 221 int msk;
222 names = cptr->info->de 222 names = cptr->info->def.type_bitmask.bit_names;
223 val &= cptr->info->def 223 val &= cptr->info->def.type_bitmask.valid_bits;
224 for (idx = 0, msk = 1; 224 for (idx = 0, msk = 1; val; idx++, msk <<= 1) {
225 if (val & msk) 225 if (val & msk) {
226 *blen 226 *blen = scnprintf(bptr,bmax,"%s",
227 227 names[idx]);
228 ret = 228 ret = 0;
229 break; 229 break;
230 } 230 }
231 } 231 }
232 } 232 }
233 } while(0); LOCK_GIVE(cptr->hdw->big_l 233 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
234 return ret; 234 return ret;
235 } 235 }
236 236
237 237
238 /* Return V4L ID for this control or zero if n 238 /* Return V4L ID for this control or zero if none */
239 int pvr2_ctrl_get_v4lid(struct pvr2_ctrl *cptr 239 int pvr2_ctrl_get_v4lid(struct pvr2_ctrl *cptr)
240 { 240 {
241 if (!cptr) return 0; 241 if (!cptr) return 0;
242 return cptr->info->v4l_id; 242 return cptr->info->v4l_id;
243 } 243 }
244 244
245 245
246 unsigned int pvr2_ctrl_get_v4lflags(struct pvr 246 unsigned int pvr2_ctrl_get_v4lflags(struct pvr2_ctrl *cptr)
247 { 247 {
248 unsigned int flags = 0; 248 unsigned int flags = 0;
249 249
250 if (cptr->info->get_v4lflags) { 250 if (cptr->info->get_v4lflags) {
251 flags = cptr->info->get_v4lfla 251 flags = cptr->info->get_v4lflags(cptr);
252 } 252 }
253 253
254 if (cptr->info->set_value) { 254 if (cptr->info->set_value) {
255 flags &= ~V4L2_CTRL_FLAG_READ_ 255 flags &= ~V4L2_CTRL_FLAG_READ_ONLY;
256 } else { 256 } else {
257 flags |= V4L2_CTRL_FLAG_READ_O 257 flags |= V4L2_CTRL_FLAG_READ_ONLY;
258 } 258 }
259 259
260 return flags; 260 return flags;
261 } 261 }
262 262
263 263
264 /* Return true if control is writable */ 264 /* Return true if control is writable */
265 int pvr2_ctrl_is_writable(struct pvr2_ctrl *cp 265 int pvr2_ctrl_is_writable(struct pvr2_ctrl *cptr)
266 { 266 {
267 if (!cptr) return 0; 267 if (!cptr) return 0;
268 return cptr->info->set_value != NULL; 268 return cptr->info->set_value != NULL;
269 } 269 }
270 270
271 271
272 /* Return true if control has custom symbolic 272 /* Return true if control has custom symbolic representation */
273 int pvr2_ctrl_has_custom_symbols(struct pvr2_c 273 int pvr2_ctrl_has_custom_symbols(struct pvr2_ctrl *cptr)
274 { 274 {
275 if (!cptr) return 0; 275 if (!cptr) return 0;
276 if (!cptr->info->val_to_sym) return 0; 276 if (!cptr->info->val_to_sym) return 0;
277 if (!cptr->info->sym_to_val) return 0; 277 if (!cptr->info->sym_to_val) return 0;
278 return !0; 278 return !0;
279 } 279 }
280 280
281 281
282 /* Convert a given mask/val to a custom symbol 282 /* Convert a given mask/val to a custom symbolic value */
283 int pvr2_ctrl_custom_value_to_sym(struct pvr2_ 283 int pvr2_ctrl_custom_value_to_sym(struct pvr2_ctrl *cptr,
284 int mask,int 284 int mask,int val,
285 char *buf,un 285 char *buf,unsigned int maxlen,
286 unsigned int 286 unsigned int *len)
287 { 287 {
288 if (!cptr) return -EINVAL; 288 if (!cptr) return -EINVAL;
289 if (!cptr->info->val_to_sym) return -E 289 if (!cptr->info->val_to_sym) return -EINVAL;
290 return cptr->info->val_to_sym(cptr,mas 290 return cptr->info->val_to_sym(cptr,mask,val,buf,maxlen,len);
291 } 291 }
292 292
293 293
294 /* Convert a symbolic value to a mask/value pa 294 /* Convert a symbolic value to a mask/value pair */
295 int pvr2_ctrl_custom_sym_to_value(struct pvr2_ 295 int pvr2_ctrl_custom_sym_to_value(struct pvr2_ctrl *cptr,
296 const char * 296 const char *buf,unsigned int len,
297 int *maskptr 297 int *maskptr,int *valptr)
298 { 298 {
299 if (!cptr) return -EINVAL; 299 if (!cptr) return -EINVAL;
300 if (!cptr->info->sym_to_val) return -E 300 if (!cptr->info->sym_to_val) return -EINVAL;
301 return cptr->info->sym_to_val(cptr,buf 301 return cptr->info->sym_to_val(cptr,buf,len,maskptr,valptr);
302 } 302 }
303 303
304 304
305 static unsigned int gen_bitmask_string(int msk 305 static unsigned int gen_bitmask_string(int msk,int val,int msk_only,
306 const c 306 const char **names,
307 char *p 307 char *ptr,unsigned int len)
308 { 308 {
309 unsigned int idx; 309 unsigned int idx;
310 long sm,um; 310 long sm,um;
311 int spcFl; 311 int spcFl;
312 unsigned int uc,cnt; 312 unsigned int uc,cnt;
313 const char *idStr; 313 const char *idStr;
314 314
315 spcFl = 0; 315 spcFl = 0;
316 uc = 0; 316 uc = 0;
317 um = 0; 317 um = 0;
318 for (idx = 0, sm = 1; msk; idx++, sm < 318 for (idx = 0, sm = 1; msk; idx++, sm <<= 1) {
319 if (sm & msk) { 319 if (sm & msk) {
320 msk &= ~sm; 320 msk &= ~sm;
321 idStr = names[idx]; 321 idStr = names[idx];
322 if (idStr) { 322 if (idStr) {
323 cnt = scnprint 323 cnt = scnprintf(ptr,len,"%s%s%s",
324 324 (spcFl ? " " : ""),
325 325 (msk_only ? "" :
326 326 ((val & sm) ? "+" : "-")),
327 327 idStr);
328 ptr += cnt; le 328 ptr += cnt; len -= cnt; uc += cnt;
329 spcFl = !0; 329 spcFl = !0;
330 } else { 330 } else {
331 um |= sm; 331 um |= sm;
332 } 332 }
333 } 333 }
334 } 334 }
335 if (um) { 335 if (um) {
336 if (msk_only) { 336 if (msk_only) {
337 cnt = scnprintf(ptr,le 337 cnt = scnprintf(ptr,len,"%s0x%lx",
338 (spcFl 338 (spcFl ? " " : ""),
339 um); 339 um);
340 ptr += cnt; len -= cnt 340 ptr += cnt; len -= cnt; uc += cnt;
341 spcFl = !0; 341 spcFl = !0;
342 } else if (um & val) { 342 } else if (um & val) {
343 cnt = scnprintf(ptr,le 343 cnt = scnprintf(ptr,len,"%s+0x%lx",
344 (spcFl 344 (spcFl ? " " : ""),
345 um & v 345 um & val);
346 ptr += cnt; len -= cnt 346 ptr += cnt; len -= cnt; uc += cnt;
347 spcFl = !0; 347 spcFl = !0;
348 } else if (um & ~val) { 348 } else if (um & ~val) {
349 cnt = scnprintf(ptr,le 349 cnt = scnprintf(ptr,len,"%s+0x%lx",
350 (spcFl 350 (spcFl ? " " : ""),
351 um & ~ 351 um & ~val);
352 ptr += cnt; len -= cnt 352 ptr += cnt; len -= cnt; uc += cnt;
353 spcFl = !0; 353 spcFl = !0;
354 } 354 }
355 } 355 }
356 return uc; 356 return uc;
357 } 357 }
358 358
359 359
360 static const char *boolNames[] = { 360 static const char *boolNames[] = {
361 "false", 361 "false",
362 "true", 362 "true",
363 "no", 363 "no",
364 "yes", 364 "yes",
365 }; 365 };
366 366
367 367
368 static int parse_token(const char *ptr,unsigne 368 static int parse_token(const char *ptr,unsigned int len,
369 int *valptr, 369 int *valptr,
370 const char **names,unsi 370 const char **names,unsigned int namecnt)
371 { 371 {
372 char buf[33]; 372 char buf[33];
373 unsigned int slen; 373 unsigned int slen;
374 unsigned int idx; 374 unsigned int idx;
375 int negfl; 375 int negfl;
376 char *p2; 376 char *p2;
377 *valptr = 0; 377 *valptr = 0;
378 if (!names) namecnt = 0; 378 if (!names) namecnt = 0;
379 for (idx = 0; idx < namecnt; idx++) { 379 for (idx = 0; idx < namecnt; idx++) {
380 if (!names[idx]) continue; 380 if (!names[idx]) continue;
381 slen = strlen(names[idx]); 381 slen = strlen(names[idx]);
382 if (slen != len) continue; 382 if (slen != len) continue;
383 if (memcmp(names[idx],ptr,slen 383 if (memcmp(names[idx],ptr,slen)) continue;
384 *valptr = idx; 384 *valptr = idx;
385 return 0; 385 return 0;
386 } 386 }
387 negfl = 0; 387 negfl = 0;
388 if ((*ptr == '-') || (*ptr == '+')) { 388 if ((*ptr == '-') || (*ptr == '+')) {
389 negfl = (*ptr == '-'); 389 negfl = (*ptr == '-');
390 ptr++; len--; 390 ptr++; len--;
391 } 391 }
392 if (len >= sizeof(buf)) return -EINVAL 392 if (len >= sizeof(buf)) return -EINVAL;
393 memcpy(buf,ptr,len); 393 memcpy(buf,ptr,len);
394 buf[len] = 0; 394 buf[len] = 0;
395 *valptr = simple_strtol(buf,&p2,0); 395 *valptr = simple_strtol(buf,&p2,0);
396 if (negfl) *valptr = -(*valptr); 396 if (negfl) *valptr = -(*valptr);
397 if (*p2) return -EINVAL; 397 if (*p2) return -EINVAL;
398 return 1; 398 return 1;
399 } 399 }
400 400
401 401
402 static int parse_mtoken(const char *ptr,unsign 402 static int parse_mtoken(const char *ptr,unsigned int len,
403 int *valptr, 403 int *valptr,
404 const char **names,int 404 const char **names,int valid_bits)
405 { 405 {
406 char buf[33]; 406 char buf[33];
407 unsigned int slen; 407 unsigned int slen;
408 unsigned int idx; 408 unsigned int idx;
409 char *p2; 409 char *p2;
410 int msk; 410 int msk;
411 *valptr = 0; 411 *valptr = 0;
412 for (idx = 0, msk = 1; valid_bits; idx 412 for (idx = 0, msk = 1; valid_bits; idx++, msk <<= 1) {
413 if (!(msk & valid_bits)) conti 413 if (!(msk & valid_bits)) continue;
414 valid_bits &= ~msk; 414 valid_bits &= ~msk;
415 if (!names[idx]) continue; 415 if (!names[idx]) continue;
416 slen = strlen(names[idx]); 416 slen = strlen(names[idx]);
417 if (slen != len) continue; 417 if (slen != len) continue;
418 if (memcmp(names[idx],ptr,slen 418 if (memcmp(names[idx],ptr,slen)) continue;
419 *valptr = msk; 419 *valptr = msk;
420 return 0; 420 return 0;
421 } 421 }
422 if (len >= sizeof(buf)) return -EINVAL 422 if (len >= sizeof(buf)) return -EINVAL;
423 memcpy(buf,ptr,len); 423 memcpy(buf,ptr,len);
424 buf[len] = 0; 424 buf[len] = 0;
425 *valptr = simple_strtol(buf,&p2,0); 425 *valptr = simple_strtol(buf,&p2,0);
426 if (*p2) return -EINVAL; 426 if (*p2) return -EINVAL;
427 return 0; 427 return 0;
428 } 428 }
429 429
430 430
431 static int parse_tlist(const char *ptr,unsigne 431 static int parse_tlist(const char *ptr,unsigned int len,
432 int *maskptr,int *valpt 432 int *maskptr,int *valptr,
433 const char **names,int 433 const char **names,int valid_bits)
434 { 434 {
435 unsigned int cnt; 435 unsigned int cnt;
436 int mask,val,kv,mode,ret; 436 int mask,val,kv,mode,ret;
437 mask = 0; 437 mask = 0;
438 val = 0; 438 val = 0;
439 ret = 0; 439 ret = 0;
440 while (len) { 440 while (len) {
441 cnt = 0; 441 cnt = 0;
442 while ((cnt < len) && 442 while ((cnt < len) &&
443 ((ptr[cnt] <= 32) || 443 ((ptr[cnt] <= 32) ||
444 (ptr[cnt] >= 127))) cn 444 (ptr[cnt] >= 127))) cnt++;
445 ptr += cnt; 445 ptr += cnt;
446 len -= cnt; 446 len -= cnt;
447 mode = 0; 447 mode = 0;
448 if ((*ptr == '-') || (*ptr == 448 if ((*ptr == '-') || (*ptr == '+')) {
449 mode = (*ptr == '-') ? 449 mode = (*ptr == '-') ? -1 : 1;
450 ptr++; 450 ptr++;
451 len--; 451 len--;
452 } 452 }
453 cnt = 0; 453 cnt = 0;
454 while (cnt < len) { 454 while (cnt < len) {
455 if (ptr[cnt] <= 32) br 455 if (ptr[cnt] <= 32) break;
456 if (ptr[cnt] >= 127) b 456 if (ptr[cnt] >= 127) break;
457 cnt++; 457 cnt++;
458 } 458 }
459 if (!cnt) break; 459 if (!cnt) break;
460 if (parse_mtoken(ptr,cnt,&kv,n 460 if (parse_mtoken(ptr,cnt,&kv,names,valid_bits)) {
461 ret = -EINVAL; 461 ret = -EINVAL;
462 break; 462 break;
463 } 463 }
464 ptr += cnt; 464 ptr += cnt;
465 len -= cnt; 465 len -= cnt;
466 switch (mode) { 466 switch (mode) {
467 case 0: 467 case 0:
468 mask = valid_bits; 468 mask = valid_bits;
469 val |= kv; 469 val |= kv;
470 break; 470 break;
471 case -1: 471 case -1:
472 mask |= kv; 472 mask |= kv;
473 val &= ~kv; 473 val &= ~kv;
474 break; 474 break;
475 case 1: 475 case 1:
476 mask |= kv; 476 mask |= kv;
477 val |= kv; 477 val |= kv;
478 break; 478 break;
479 default: 479 default:
480 break; 480 break;
481 } 481 }
482 } 482 }
483 *maskptr = mask; 483 *maskptr = mask;
484 *valptr = val; 484 *valptr = val;
485 return ret; 485 return ret;
486 } 486 }
487 487
488 488
489 /* Convert a symbolic value to a mask/value pa 489 /* Convert a symbolic value to a mask/value pair */
490 int pvr2_ctrl_sym_to_value(struct pvr2_ctrl *c 490 int pvr2_ctrl_sym_to_value(struct pvr2_ctrl *cptr,
491 const char *ptr,uns 491 const char *ptr,unsigned int len,
492 int *maskptr,int *v 492 int *maskptr,int *valptr)
493 { 493 {
494 int ret = -EINVAL; 494 int ret = -EINVAL;
495 unsigned int cnt; 495 unsigned int cnt;
496 496
497 *maskptr = 0; 497 *maskptr = 0;
498 *valptr = 0; 498 *valptr = 0;
499 499
500 cnt = 0; 500 cnt = 0;
501 while ((cnt < len) && ((ptr[cnt] <= 32 501 while ((cnt < len) && ((ptr[cnt] <= 32) || (ptr[cnt] >= 127))) cnt++;
502 len -= cnt; ptr += cnt; 502 len -= cnt; ptr += cnt;
503 cnt = 0; 503 cnt = 0;
504 while ((cnt < len) && ((ptr[len-(cnt+1 504 while ((cnt < len) && ((ptr[len-(cnt+1)] <= 32) ||
505 (ptr[len-(cnt+1 505 (ptr[len-(cnt+1)] >= 127))) cnt++;
506 len -= cnt; 506 len -= cnt;
507 507
508 if (!len) return -EINVAL; 508 if (!len) return -EINVAL;
509 509
510 LOCK_TAKE(cptr->hdw->big_lock); do { 510 LOCK_TAKE(cptr->hdw->big_lock); do {
511 if (cptr->info->type == pvr2_c 511 if (cptr->info->type == pvr2_ctl_int) {
512 ret = parse_token(ptr, 512 ret = parse_token(ptr,len,valptr,NULL,0);
513 if (ret >= 0) { 513 if (ret >= 0) {
514 ret = pvr2_ctr 514 ret = pvr2_ctrl_range_check(cptr,*valptr);
515 } 515 }
516 if (maskptr) *maskptr 516 if (maskptr) *maskptr = ~0;
517 } else if (cptr->info->type == 517 } else if (cptr->info->type == pvr2_ctl_bool) {
518 ret = parse_token(ptr, 518 ret = parse_token(ptr,len,valptr,boolNames,
519 ARRA 519 ARRAY_SIZE(boolNames));
520 if (ret == 1) { 520 if (ret == 1) {
521 *valptr = *val 521 *valptr = *valptr ? !0 : 0;
522 } else if (ret == 0) { 522 } else if (ret == 0) {
523 *valptr = (*va 523 *valptr = (*valptr & 1) ? !0 : 0;
524 } 524 }
525 if (maskptr) *maskptr 525 if (maskptr) *maskptr = 1;
526 } else if (cptr->info->type == 526 } else if (cptr->info->type == pvr2_ctl_enum) {
527 ret = parse_token( 527 ret = parse_token(
528 ptr,len,valptr 528 ptr,len,valptr,
529 cptr->info->de 529 cptr->info->def.type_enum.value_names,
530 cptr->info->de 530 cptr->info->def.type_enum.count);
531 if ((ret >= 0) && !! 531 if (ret >= 0) {
532 ((*valptr < 0) || !! 532 ret = pvr2_ctrl_range_check(cptr,*valptr);
533 (*valptr >= cptr- <<
534 ret = -ERANGE; <<
535 } 533 }
536 if (maskptr) *maskptr 534 if (maskptr) *maskptr = ~0;
537 } else if (cptr->info->type == 535 } else if (cptr->info->type == pvr2_ctl_bitmask) {
538 ret = parse_tlist( 536 ret = parse_tlist(
539 ptr,len,maskpt 537 ptr,len,maskptr,valptr,
540 cptr->info->de 538 cptr->info->def.type_bitmask.bit_names,
541 cptr->info->de 539 cptr->info->def.type_bitmask.valid_bits);
542 } 540 }
543 } while(0); LOCK_GIVE(cptr->hdw->big_l 541 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
544 return ret; 542 return ret;
545 } 543 }
546 544
547 545
548 /* Convert a given mask/val to a symbolic valu 546 /* Convert a given mask/val to a symbolic value */
549 int pvr2_ctrl_value_to_sym_internal(struct pvr 547 int pvr2_ctrl_value_to_sym_internal(struct pvr2_ctrl *cptr,
550 int mask,i 548 int mask,int val,
551 char *buf, 549 char *buf,unsigned int maxlen,
552 unsigned i 550 unsigned int *len)
553 { 551 {
554 int ret = -EINVAL; 552 int ret = -EINVAL;
555 553
556 *len = 0; 554 *len = 0;
557 if (cptr->info->type == pvr2_ctl_int) 555 if (cptr->info->type == pvr2_ctl_int) {
558 *len = scnprintf(buf,maxlen,"% 556 *len = scnprintf(buf,maxlen,"%d",val);
559 ret = 0; 557 ret = 0;
560 } else if (cptr->info->type == pvr2_ct 558 } else if (cptr->info->type == pvr2_ctl_bool) {
561 *len = scnprintf(buf,maxlen,"% 559 *len = scnprintf(buf,maxlen,"%s",val ? "true" : "false");
562 ret = 0; 560 ret = 0;
563 } else if (cptr->info->type == pvr2_ct 561 } else if (cptr->info->type == pvr2_ctl_enum) {
564 const char **names; 562 const char **names;
565 names = cptr->info->def.type_e 563 names = cptr->info->def.type_enum.value_names;
566 if ((val >= 0) && 564 if ((val >= 0) &&
567 (val < cptr->info->def.typ 565 (val < cptr->info->def.type_enum.count)) {
568 if (names[val]) { 566 if (names[val]) {
569 *len = scnprin 567 *len = scnprintf(
570 buf,ma 568 buf,maxlen,"%s",
571 names[ 569 names[val]);
572 } else { 570 } else {
573 *len = 0; 571 *len = 0;
574 } 572 }
575 ret = 0; 573 ret = 0;
576 } 574 }
577 } else if (cptr->info->type == pvr2_ct 575 } else if (cptr->info->type == pvr2_ctl_bitmask) {
578 *len = gen_bitmask_string( 576 *len = gen_bitmask_string(
579 val & mask & cptr->inf 577 val & mask & cptr->info->def.type_bitmask.valid_bits,
580 ~0,!0, 578 ~0,!0,
581 cptr->info->def.type_b 579 cptr->info->def.type_bitmask.bit_names,
582 buf,maxlen); 580 buf,maxlen);
583 } 581 }
584 return ret; 582 return ret;
585 } 583 }
586 584
587 585
588 /* Convert a given mask/val to a symbolic valu 586 /* Convert a given mask/val to a symbolic value */
589 int pvr2_ctrl_value_to_sym(struct pvr2_ctrl *c 587 int pvr2_ctrl_value_to_sym(struct pvr2_ctrl *cptr,
590 int mask,int val, 588 int mask,int val,
591 char *buf,unsigned 589 char *buf,unsigned int maxlen,
592 unsigned int *len) 590 unsigned int *len)
593 { 591 {
594 int ret; 592 int ret;
595 LOCK_TAKE(cptr->hdw->big_lock); do { 593 LOCK_TAKE(cptr->hdw->big_lock); do {
596 ret = pvr2_ctrl_value_to_sym_i 594 ret = pvr2_ctrl_value_to_sym_internal(cptr,mask,val,
597 595 buf,maxlen,len);
598 } while(0); LOCK_GIVE(cptr->hdw->big_l 596 } while(0); LOCK_GIVE(cptr->hdw->big_lock);
599 return ret; 597 return ret;
600 } 598 }
601 599
602 600
603 /* 601 /*
604 Stuff for Emacs to see, in order to encourag 602 Stuff for Emacs to see, in order to encourage consistent editing style:
605 *** Local Variables: *** 603 *** Local Variables: ***
606 *** mode: c *** 604 *** mode: c ***
607 *** fill-column: 75 *** 605 *** fill-column: 75 ***
608 *** tab-width: 8 *** 606 *** tab-width: 8 ***
609 *** c-basic-offset: 8 *** 607 *** c-basic-offset: 8 ***
610 *** End: *** 608 *** End: ***
611 */ 609 */
612 610
|
This page was automatically generated by the
LXR engine.
|