linux/drivers/media/radio/radio-mr800.c

// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * A driver for the AverMedia MR 800 USB FM radio. This device plugs
 * into both the USB and an analog audio input, so this thing
 * only deals with initialization and frequency setting, the
 * audio data has to be handled by a sound driver.
 *
 * Copyright (c) 2008 Alexey Klimov <[email protected]>
 */

/*
 * Big thanks to authors and contributors of dsbr100.c and radio-si470x.c
 *
 * When work was looked pretty good, i discover this:
 * http://av-usbradio.sourceforge.net/index.php
 * http://sourceforge.net/projects/av-usbradio/
 * Latest release of theirs project was in 2005.
 * Probably, this driver could be improved through using their
 * achievements (specifications given).
 * Also, Faidon Liambotis <[email protected]> wrote nice driver for this radio
 * in 2007. He allowed to use his driver to improve current mr800 radio driver.
 * http://www.spinics.net/lists/linux-usb-devel/msg10109.html
 *
 * Version 0.01:	First working version.
 *			It's required to blacklist AverMedia USB Radio
 *			in usbhid/hid-quirks.c
 * Version 0.10:	A lot of cleanups and fixes: unpluging the device,
 *			few mutex locks were added, codinstyle issues, etc.
 *			Added stereo support. Thanks to
 *			Douglas Schilling Landgraf <[email protected]> and
 *			David Ellingsworth <[email protected]>
 *			for discussion, help and support.
 * Version 0.11:	Converted to v4l2_device.
 *
 * Many things to do:
 *	- Correct power management of device (suspend & resume)
 *	- Add code for scanning and smooth tuning
 *	- Add code for sensitivity value
 *	- Correct mistakes
 *	- In Japan another FREQ_MIN and FREQ_MAX
 */

/* kernel includes */
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/input.h>
#include <linux/videodev2.h>
#include <media/v4l2-device.h>
#include <media/v4l2-ioctl.h>
#include <media/v4l2-ctrls.h>
#include <media/v4l2-event.h>
#include <linux/usb.h>
#include <linux/mutex.h>

/* driver and module definitions */
#define DRIVER_AUTHOR
#define DRIVER_DESC
#define DRIVER_VERSION

MODULE_AUTHOR();
MODULE_DESCRIPTION();
MODULE_LICENSE();
MODULE_VERSION();

#define USB_AMRADIO_VENDOR
#define USB_AMRADIO_PRODUCT

/* dev_warn macro with driver name */
#define MR800_DRIVER_NAME
#define amradio_dev_warn(dev, fmt, arg...)

#define amradio_dev_err(dev, fmt, arg...)

/* Probably USB_TIMEOUT should be modified in module parameter */
#define BUFFER_LENGTH
#define USB_TIMEOUT

/* Frequency limits in MHz -- these are European values.  For Japanese
devices, that would be 76 and 91.  */
#define FREQ_MIN
#define FREQ_MAX
#define FREQ_MUL

/*
 * Commands that device should understand
 * List isn't full and will be updated with implementation of new functions
 */
#define AMRADIO_SET_FREQ
#define AMRADIO_GET_READY_FLAG
#define AMRADIO_GET_SIGNAL
#define AMRADIO_GET_FREQ
#define AMRADIO_SET_SEARCH_UP
#define AMRADIO_SET_SEARCH_DOWN
#define AMRADIO_SET_MUTE
#define AMRADIO_SET_RIGHT_MUTE
#define AMRADIO_SET_LEFT_MUTE
#define AMRADIO_SET_MONO
#define AMRADIO_SET_SEARCH_LVL
#define AMRADIO_STOP_SEARCH

/* Comfortable defines for amradio_set_stereo */
#define WANT_STEREO
#define WANT_MONO

/* module parameter */
static int radio_nr =;
module_param(radio_nr, int, 0);
MODULE_PARM_DESC();

/* Data for one (physical) device */
struct amradio_device {};

static inline struct amradio_device *to_amradio_dev(struct v4l2_device *v4l2_dev)
{}

static int amradio_send_cmd(struct amradio_device *radio, u8 cmd, u8 arg,
		u8 *extra, u8 extralen, bool reply)
{}

/* switch on/off the radio. Send 8 bytes to device */
static int amradio_set_mute(struct amradio_device *radio, bool mute)
{}

/* set a frequency, freq is defined by v4l's TUNER_LOW, i.e. 1/16th kHz */
static int amradio_set_freq(struct amradio_device *radio, int freq)
{}

static int amradio_set_stereo(struct amradio_device *radio, bool stereo)
{}

static int amradio_get_stat(struct amradio_device *radio, bool *is_stereo, u32 *signal)
{}

/* Handle unplugging the device.
 * We call video_unregister_device in any case.
 * The last function called in this procedure is
 * usb_amradio_device_release.
 */
static void usb_amradio_disconnect(struct usb_interface *intf)
{}

/* vidioc_querycap - query device capabilities */
static int vidioc_querycap(struct file *file, void *priv,
					struct v4l2_capability *v)
{}

/* vidioc_g_tuner - get tuner attributes */
static int vidioc_g_tuner(struct file *file, void *priv,
				struct v4l2_tuner *v)
{}

/* vidioc_s_tuner - set tuner attributes */
static int vidioc_s_tuner(struct file *file, void *priv,
				const struct v4l2_tuner *v)
{}

/* vidioc_s_frequency - set tuner radio frequency */
static int vidioc_s_frequency(struct file *file, void *priv,
				const struct v4l2_frequency *f)
{}

/* vidioc_g_frequency - get tuner radio frequency */
static int vidioc_g_frequency(struct file *file, void *priv,
				struct v4l2_frequency *f)
{}

static int vidioc_s_hw_freq_seek(struct file *file, void *priv,
		const struct v4l2_hw_freq_seek *seek)
{}

static int usb_amradio_s_ctrl(struct v4l2_ctrl *ctrl)
{}

static int usb_amradio_init(struct amradio_device *radio)
{}

/* Suspend device - stop device. Need to be checked and fixed */
static int usb_amradio_suspend(struct usb_interface *intf, pm_message_t message)
{}

/* Resume device - start device. Need to be checked and fixed */
static int usb_amradio_resume(struct usb_interface *intf)
{}

static const struct v4l2_ctrl_ops usb_amradio_ctrl_ops =;

/* File system interface */
static const struct v4l2_file_operations usb_amradio_fops =;

static const struct v4l2_ioctl_ops usb_amradio_ioctl_ops =;

static void usb_amradio_release(struct v4l2_device *v4l2_dev)
{}

/* check if the device is present and register with v4l and usb if it is */
static int usb_amradio_probe(struct usb_interface *intf,
				const struct usb_device_id *id)
{}

/* USB Device ID List */
static const struct usb_device_id usb_amradio_device_table[] =;

MODULE_DEVICE_TABLE(usb, usb_amradio_device_table);

/* USB subsystem interface */
static struct usb_driver usb_amradio_driver =;

module_usb_driver();