diff options
Diffstat (limited to 'drivers/media')
-rw-r--r-- | drivers/media/radio/radio-zoltrix.c | 256 |
1 files changed, 145 insertions, 111 deletions
diff --git a/drivers/media/radio/radio-zoltrix.c b/drivers/media/radio/radio-zoltrix.c index ec08491fb7c5..a4715901512d 100644 --- a/drivers/media/radio/radio-zoltrix.c +++ b/drivers/media/radio/radio-zoltrix.c | |||
@@ -230,121 +230,123 @@ static int zol_is_stereo (struct zol_device *dev) | |||
230 | return 0; | 230 | return 0; |
231 | } | 231 | } |
232 | 232 | ||
233 | static int zol_do_ioctl(struct inode *inode, struct file *file, | 233 | static int vidioc_querycap(struct file *file, void *priv, |
234 | unsigned int cmd, void *arg) | 234 | struct v4l2_capability *v) |
235 | { | ||
236 | strlcpy(v->driver, "radio-zoltrix", sizeof(v->driver)); | ||
237 | strlcpy(v->card, "Zoltrix Radio", sizeof(v->card)); | ||
238 | sprintf(v->bus_info, "ISA"); | ||
239 | v->version = RADIO_VERSION; | ||
240 | v->capabilities = V4L2_CAP_TUNER; | ||
241 | return 0; | ||
242 | } | ||
243 | |||
244 | static int vidioc_g_tuner(struct file *file, void *priv, | ||
245 | struct v4l2_tuner *v) | ||
235 | { | 246 | { |
236 | struct video_device *dev = video_devdata(file); | 247 | struct video_device *dev = video_devdata(file); |
237 | struct zol_device *zol = dev->priv; | 248 | struct zol_device *zol = dev->priv; |
238 | 249 | ||
239 | switch (cmd) { | 250 | if (v->index > 0) |
240 | case VIDIOC_QUERYCAP: | 251 | return -EINVAL; |
241 | { | ||
242 | struct v4l2_capability *v = arg; | ||
243 | memset(v,0,sizeof(*v)); | ||
244 | strlcpy(v->driver, "radio-zoltrix", sizeof (v->driver)); | ||
245 | strlcpy(v->card, "Zoltrix Radio", sizeof (v->card)); | ||
246 | sprintf(v->bus_info,"ISA"); | ||
247 | v->version = RADIO_VERSION; | ||
248 | v->capabilities = V4L2_CAP_TUNER; | ||
249 | 252 | ||
250 | return 0; | 253 | strcpy(v->name, "FM"); |
251 | } | 254 | v->type = V4L2_TUNER_RADIO; |
252 | case VIDIOC_G_TUNER: | 255 | v->rangelow = (88*16000); |
253 | { | 256 | v->rangehigh = (108*16000); |
254 | struct v4l2_tuner *v = arg; | 257 | v->rxsubchans = V4L2_TUNER_SUB_MONO|V4L2_TUNER_SUB_STEREO; |
255 | 258 | v->capability = V4L2_TUNER_CAP_LOW; | |
256 | if (v->index > 0) | 259 | if (zol_is_stereo(zol)) |
257 | return -EINVAL; | 260 | v->audmode = V4L2_TUNER_MODE_STEREO; |
258 | 261 | else | |
259 | memset(v,0,sizeof(*v)); | 262 | v->audmode = V4L2_TUNER_MODE_MONO; |
260 | strcpy(v->name, "FM"); | 263 | v->signal = 0xFFFF*zol_getsigstr(zol); |
261 | v->type = V4L2_TUNER_RADIO; | 264 | return 0; |
262 | 265 | } | |
263 | v->rangelow=(88*16000); | ||
264 | v->rangehigh=(108*16000); | ||
265 | v->rxsubchans =V4L2_TUNER_SUB_MONO|V4L2_TUNER_SUB_STEREO; | ||
266 | v->capability=V4L2_TUNER_CAP_LOW; | ||
267 | if(zol_is_stereo(zol)) | ||
268 | v->audmode = V4L2_TUNER_MODE_STEREO; | ||
269 | else | ||
270 | v->audmode = V4L2_TUNER_MODE_MONO; | ||
271 | v->signal=0xFFFF*zol_getsigstr(zol); | ||
272 | 266 | ||
273 | return 0; | 267 | static int vidioc_s_tuner(struct file *file, void *priv, |
274 | } | 268 | struct v4l2_tuner *v) |
275 | case VIDIOC_S_TUNER: | 269 | { |
276 | { | 270 | if (v->index > 0) |
277 | struct v4l2_tuner *v = arg; | 271 | return -EINVAL; |
272 | return 0; | ||
273 | } | ||
278 | 274 | ||
279 | if (v->index > 0) | 275 | static int vidioc_s_frequency(struct file *file, void *priv, |
280 | return -EINVAL; | 276 | struct v4l2_frequency *f) |
277 | { | ||
278 | struct video_device *dev = video_devdata(file); | ||
279 | struct zol_device *zol = dev->priv; | ||
281 | 280 | ||
282 | return 0; | 281 | zol->curfreq = f->frequency; |
283 | } | 282 | zol_setfreq(zol, zol->curfreq); |
284 | case VIDIOC_S_FREQUENCY: | 283 | return 0; |
285 | { | 284 | } |
286 | struct v4l2_frequency *f = arg; | ||
287 | 285 | ||
288 | zol->curfreq = f->frequency; | 286 | static int vidioc_g_frequency(struct file *file, void *priv, |
289 | zol_setfreq(zol, zol->curfreq); | 287 | struct v4l2_frequency *f) |
290 | return 0; | 288 | { |
291 | } | 289 | struct video_device *dev = video_devdata(file); |
292 | case VIDIOC_G_FREQUENCY: | 290 | struct zol_device *zol = dev->priv; |
293 | { | 291 | |
294 | struct v4l2_frequency *f = arg; | 292 | f->type = V4L2_TUNER_RADIO; |
293 | f->frequency = zol->curfreq; | ||
294 | return 0; | ||
295 | } | ||
295 | 296 | ||
296 | f->type = V4L2_TUNER_RADIO; | 297 | static int vidioc_queryctrl(struct file *file, void *priv, |
297 | f->frequency = zol->curfreq; | 298 | struct v4l2_queryctrl *qc) |
299 | { | ||
300 | int i; | ||
298 | 301 | ||
302 | for (i = 0; i < ARRAY_SIZE(radio_qctrl); i++) { | ||
303 | if (qc->id && qc->id == radio_qctrl[i].id) { | ||
304 | memcpy(qc, &(radio_qctrl[i]), | ||
305 | sizeof(*qc)); | ||
299 | return 0; | 306 | return 0; |
300 | } | 307 | } |
301 | case VIDIOC_QUERYCTRL: | 308 | } |
302 | { | 309 | return -EINVAL; |
303 | struct v4l2_queryctrl *qc = arg; | 310 | } |
304 | int i; | 311 | |
305 | 312 | static int vidioc_g_ctrl(struct file *file, void *priv, | |
306 | for (i = 0; i < ARRAY_SIZE(radio_qctrl); i++) { | 313 | struct v4l2_control *ctrl) |
307 | if (qc->id && qc->id == radio_qctrl[i].id) { | 314 | { |
308 | memcpy(qc, &(radio_qctrl[i]), | 315 | struct video_device *dev = video_devdata(file); |
309 | sizeof(*qc)); | 316 | struct zol_device *zol = dev->priv; |
310 | return (0); | 317 | |
311 | } | 318 | switch (ctrl->id) { |
312 | } | 319 | case V4L2_CID_AUDIO_MUTE: |
313 | return -EINVAL; | 320 | ctrl->value = zol->muted; |
314 | } | 321 | return 0; |
315 | case VIDIOC_G_CTRL: | 322 | case V4L2_CID_AUDIO_VOLUME: |
316 | { | 323 | ctrl->value = zol->curvol * 4096; |
317 | struct v4l2_control *ctrl= arg; | 324 | return 0; |
318 | 325 | } | |
319 | switch (ctrl->id) { | 326 | return -EINVAL; |
320 | case V4L2_CID_AUDIO_MUTE: | 327 | } |
321 | ctrl->value=zol->muted; | 328 | |
322 | return (0); | 329 | static int vidioc_s_ctrl(struct file *file, void *priv, |
323 | case V4L2_CID_AUDIO_VOLUME: | 330 | struct v4l2_control *ctrl) |
324 | ctrl->value=zol->curvol * 4096; | 331 | { |
325 | return (0); | 332 | struct video_device *dev = video_devdata(file); |
326 | } | 333 | struct zol_device *zol = dev->priv; |
327 | return -EINVAL; | 334 | |
335 | switch (ctrl->id) { | ||
336 | case V4L2_CID_AUDIO_MUTE: | ||
337 | if (ctrl->value) | ||
338 | zol_mute(zol); | ||
339 | else { | ||
340 | zol_unmute(zol); | ||
341 | zol_setvol(zol,zol->curvol); | ||
328 | } | 342 | } |
329 | case VIDIOC_S_CTRL: | 343 | return 0; |
330 | { | 344 | case V4L2_CID_AUDIO_VOLUME: |
331 | struct v4l2_control *ctrl= arg; | 345 | zol_setvol(zol,ctrl->value/4096); |
332 | 346 | return 0; | |
333 | switch (ctrl->id) { | 347 | } |
334 | case V4L2_CID_AUDIO_MUTE: | 348 | zol->stereo = 1; |
335 | if (ctrl->value) { | 349 | zol_setfreq(zol, zol->curfreq); |
336 | zol_mute(zol); | ||
337 | } else { | ||
338 | zol_unmute(zol); | ||
339 | zol_setvol(zol,zol->curvol); | ||
340 | } | ||
341 | return (0); | ||
342 | case V4L2_CID_AUDIO_VOLUME: | ||
343 | zol_setvol(zol,ctrl->value/4096); | ||
344 | return (0); | ||
345 | } | ||
346 | zol->stereo = 1; | ||
347 | zol_setfreq(zol, zol->curfreq); | ||
348 | #if 0 | 350 | #if 0 |
349 | /* FIXME: Implement stereo/mono switch on V4L2 */ | 351 | /* FIXME: Implement stereo/mono switch on V4L2 */ |
350 | if (v->mode & VIDEO_SOUND_STEREO) { | 352 | if (v->mode & VIDEO_SOUND_STEREO) { |
@@ -356,19 +358,39 @@ static int zol_do_ioctl(struct inode *inode, struct file *file, | |||
356 | zol_setfreq(zol, zol->curfreq); | 358 | zol_setfreq(zol, zol->curfreq); |
357 | } | 359 | } |
358 | #endif | 360 | #endif |
359 | return -EINVAL; | 361 | return -EINVAL; |
360 | } | 362 | } |
361 | 363 | ||
362 | default: | 364 | static int vidioc_g_audio(struct file *file, void *priv, |
363 | return v4l_compat_translate_ioctl(inode,file,cmd,arg, | 365 | struct v4l2_audio *a) |
364 | zol_do_ioctl); | 366 | { |
365 | } | 367 | if (a->index > 1) |
368 | return -EINVAL; | ||
369 | |||
370 | strcpy(a->name, "Radio"); | ||
371 | a->capability = V4L2_AUDCAP_STEREO; | ||
372 | return 0; | ||
373 | } | ||
374 | |||
375 | static int vidioc_g_input(struct file *filp, void *priv, unsigned int *i) | ||
376 | { | ||
377 | *i = 0; | ||
378 | return 0; | ||
366 | } | 379 | } |
367 | 380 | ||
368 | static int zol_ioctl(struct inode *inode, struct file *file, | 381 | static int vidioc_s_input(struct file *filp, void *priv, unsigned int i) |
369 | unsigned int cmd, unsigned long arg) | ||
370 | { | 382 | { |
371 | return video_usercopy(inode, file, cmd, arg, zol_do_ioctl); | 383 | if (i != 0) |
384 | return -EINVAL; | ||
385 | return 0; | ||
386 | } | ||
387 | |||
388 | static int vidioc_s_audio(struct file *file, void *priv, | ||
389 | struct v4l2_audio *a) | ||
390 | { | ||
391 | if (a->index != 0) | ||
392 | return -EINVAL; | ||
393 | return 0; | ||
372 | } | 394 | } |
373 | 395 | ||
374 | static struct zol_device zoltrix_unit; | 396 | static struct zol_device zoltrix_unit; |
@@ -378,7 +400,7 @@ static const struct file_operations zoltrix_fops = | |||
378 | .owner = THIS_MODULE, | 400 | .owner = THIS_MODULE, |
379 | .open = video_exclusive_open, | 401 | .open = video_exclusive_open, |
380 | .release = video_exclusive_release, | 402 | .release = video_exclusive_release, |
381 | .ioctl = zol_ioctl, | 403 | .ioctl = video_ioctl2, |
382 | .compat_ioctl = v4l_compat_ioctl32, | 404 | .compat_ioctl = v4l_compat_ioctl32, |
383 | .llseek = no_llseek, | 405 | .llseek = no_llseek, |
384 | }; | 406 | }; |
@@ -390,6 +412,18 @@ static struct video_device zoltrix_radio = | |||
390 | .type = VID_TYPE_TUNER, | 412 | .type = VID_TYPE_TUNER, |
391 | .hardware = 0, | 413 | .hardware = 0, |
392 | .fops = &zoltrix_fops, | 414 | .fops = &zoltrix_fops, |
415 | .vidioc_querycap = vidioc_querycap, | ||
416 | .vidioc_g_tuner = vidioc_g_tuner, | ||
417 | .vidioc_s_tuner = vidioc_s_tuner, | ||
418 | .vidioc_g_audio = vidioc_g_audio, | ||
419 | .vidioc_s_audio = vidioc_s_audio, | ||
420 | .vidioc_g_input = vidioc_g_input, | ||
421 | .vidioc_s_input = vidioc_s_input, | ||
422 | .vidioc_g_frequency = vidioc_g_frequency, | ||
423 | .vidioc_s_frequency = vidioc_s_frequency, | ||
424 | .vidioc_queryctrl = vidioc_queryctrl, | ||
425 | .vidioc_g_ctrl = vidioc_g_ctrl, | ||
426 | .vidioc_s_ctrl = vidioc_s_ctrl, | ||
393 | }; | 427 | }; |
394 | 428 | ||
395 | static int __init zoltrix_init(void) | 429 | static int __init zoltrix_init(void) |