summaryrefslogtreecommitdiff
path: root/drivers/staging/tm6000/tm6000.h
blob: 7bbaf26dea14f292b1808820698a702981514ebe (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
/*
   tm6000.h - driver for TM5600/TM6000/TM6010 USB video capture devices

   Copyright (C) 2006-2007 Mauro Carvalho Chehab <mchehab@infradead.org>

   Copyright (C) 2007 Michel Ludwig <michel.ludwig@gmail.com>
	- DVB-T support

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation version 2

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */

// Use the tm6000-hack, instead of the proper initialization code
//#define HACK 1

#include <linux/videodev2.h>
#include <media/v4l2-common.h>
#include <media/videobuf-vmalloc.h>
#include "tm6000-usb-isoc.h"
#include <linux/i2c.h>
#include <linux/mutex.h>
#include <media/v4l2-device.h>


#include <linux/dvb/frontend.h>
#include "dvb_demux.h"
#include "dvb_frontend.h"
#include "dmxdev.h"

#define TM6000_VERSION KERNEL_VERSION(0, 0, 2)

/* Inputs */

enum tm6000_itype {
	TM6000_INPUT_TV	= 0,
	TM6000_INPUT_COMPOSITE,
	TM6000_INPUT_SVIDEO,
};

enum tm6000_devtype {
	TM6000 = 0,
	TM5600,
	TM6010,
};

/* ------------------------------------------------------------------
	Basic structures
   ------------------------------------------------------------------*/

struct tm6000_fmt {
	char  *name;
	u32   fourcc;          /* v4l2 format id */
	int   depth;
};

/* buffer for one video frame */
struct tm6000_buffer {
	/* common v4l buffer stuff -- must be first */
	struct videobuf_buffer vb;

	struct tm6000_fmt      *fmt;
};

struct tm6000_dmaqueue {
	struct list_head       active;
	struct list_head       queued;

	/* thread for generating video stream*/
	struct task_struct         *kthread;
	wait_queue_head_t          wq;
	/* Counters to control fps rate */
	int                        frame;
	int                        ini_jiffies;
};

/* device states */
enum tm6000_core_state {
	DEV_INITIALIZED   = 0x01,
	DEV_DISCONNECTED  = 0x02,
	DEV_MISCONFIGURED = 0x04,
};

/* io methods */
enum tm6000_io_method {
	IO_NONE,
	IO_READ,
	IO_MMAP,
};

enum tm6000_mode {
	TM6000_MODE_UNKNOWN=0,
	TM6000_MODE_ANALOG,
	TM6000_MODE_DIGITAL,
};

struct tm6000_gpio {
	int		tuner_reset;
	int		tuner_on;
	int		demod_reset;
	int		demod_on;
	int		power_led;
	int		dvb_led;
	int		ir;
};

struct tm6000_capabilities {
	unsigned int    has_tuner:1;
	unsigned int    has_tda9874:1;
	unsigned int    has_dvb:1;
	unsigned int    has_zl10353:1;
	unsigned int    has_eeprom:1;
	unsigned int    has_remote:1;
};

struct tm6000_dvb {
	struct dvb_adapter	adapter;
	struct dvb_demux	demux;
	struct dvb_frontend	*frontend;
	struct dmxdev		dmxdev;
	unsigned int		streams;
	struct urb 		*bulk_urb;
	struct mutex		mutex;
};

struct tm6000_endpoint {
	struct usb_host_endpoint	*endp;
	__u8				bInterfaceNumber;
	__u8				bAlternateSetting;
	unsigned			maxsize;
};

struct tm6000_core {
	/* generic device properties */
	char				name[30];	/* name (including minor) of the device */
	int				model;		/* index in the device_data struct */
	int				devno;		/* marks the number of this device */
	enum tm6000_devtype		dev_type;	/* type of device */

	v4l2_std_id                     norm;           /* Current norm */
	int				width,height;	/* Selected resolution */

	enum tm6000_core_state		state;

	/* Device Capabilities*/
	struct tm6000_capabilities	caps;

	/* Tuner configuration */
	int				tuner_type;		/* type of the tuner */
	int				tuner_addr;		/* tuner address */

	struct tm6000_gpio		gpio;

	/* Demodulator configuration */
	int				demod_addr;	/* demodulator address */

	int				audio_bitrate;
	/* i2c i/o */
	struct i2c_adapter		i2c_adap;
	struct i2c_client		i2c_client;


	/* extension */
	struct list_head		devlist;

	/* video for linux */
	int				users;

	/* various device info */
	unsigned int			resources;
	struct video_device		*vfd;
	struct tm6000_dmaqueue		vidq;
	struct v4l2_device		v4l2_dev;

	int				input;
	int				freq;
	unsigned int			fourcc;

	enum tm6000_mode		mode;

	/* DVB-T support */
	struct tm6000_dvb		*dvb;

	/* locks */
	struct mutex			lock;

	/* usb transfer */
	struct usb_device		*udev;		/* the usb device */

	struct tm6000_endpoint		bulk_in, bulk_out, isoc_in, isoc_out;

	/* scaler!=0 if scaler is active*/
	int				scaler;

		/* Isoc control struct */
	struct usb_isoc_ctl          isoc_ctl;

	spinlock_t                   slock;
};

#define TM6000_AUDIO 0x10

struct tm6000_ops {
	struct list_head	next;
	char			*name;
	int			id;
	int (*init)(struct tm6000_core *);
	int (*fini)(struct tm6000_core *);
};

struct tm6000_fh {
	struct tm6000_core           *dev;

	/* video capture */
	struct tm6000_fmt            *fmt;
	unsigned int                 width,height;
	struct videobuf_queue        vb_vidq;

	enum v4l2_buf_type           type;
};

#define TM6000_STD	V4L2_STD_PAL|V4L2_STD_PAL_N|V4L2_STD_PAL_Nc|    \
			V4L2_STD_PAL_M|V4L2_STD_PAL_60|V4L2_STD_NTSC_M| \
			V4L2_STD_NTSC_M_JP|V4L2_STD_SECAM

/* In tm6000-cards.c */

int tm6000_tuner_callback (void *ptr, int component, int command, int arg);
int tm6000_xc5000_callback (void *ptr, int component, int command, int arg);
int tm6000_cards_setup(struct tm6000_core *dev);

/* In tm6000-core.c */

int tm6000_read_write_usb (struct tm6000_core *dev, u8 reqtype, u8 req,
			   u16 value, u16 index, u8 *buf, u16 len);
int tm6000_get_reg (struct tm6000_core *dev, u8 req, u16 value, u16 index);
int tm6000_get_reg16(struct tm6000_core *dev, u8 req, u16 value, u16 index);
int tm6000_get_reg32(struct tm6000_core *dev, u8 req, u16 value, u16 index);
int tm6000_set_reg (struct tm6000_core *dev, u8 req, u16 value, u16 index);
int tm6000_i2c_reset(struct tm6000_core *dev, u16 tsleep);

int tm6000_init (struct tm6000_core *dev);

int tm6000_init_analog_mode (struct tm6000_core *dev);
int tm6000_init_digital_mode (struct tm6000_core *dev);
int tm6000_set_audio_bitrate (struct tm6000_core *dev, int bitrate);

int tm6000_dvb_register(struct tm6000_core *dev);
void tm6000_dvb_unregister(struct tm6000_core *dev);

int tm6000_v4l2_register(struct tm6000_core *dev);
int tm6000_v4l2_unregister(struct tm6000_core *dev);
int tm6000_v4l2_exit(void);
void tm6000_set_fourcc_format(struct tm6000_core *dev);

void tm6000_remove_from_devlist(struct tm6000_core *dev);
void tm6000_add_into_devlist(struct tm6000_core *dev);
int tm6000_register_extension(struct tm6000_ops *ops);
void tm6000_unregister_extension(struct tm6000_ops *ops);
void tm6000_init_extension(struct tm6000_core *dev);
void tm6000_close_extension(struct tm6000_core *dev);

/* In tm6000-stds.c */
void tm6000_get_std_res(struct tm6000_core *dev);
int tm6000_set_standard (struct tm6000_core *dev, v4l2_std_id *norm);

/* In tm6000-i2c.c */
int tm6000_i2c_register(struct tm6000_core *dev);
int tm6000_i2c_unregister(struct tm6000_core *dev);

/* In tm6000-queue.c */

int tm6000_v4l2_mmap(struct file *filp, struct vm_area_struct *vma);

int tm6000_vidioc_streamon(struct file *file, void *priv,
			   enum v4l2_buf_type i);
int tm6000_vidioc_streamoff(struct file *file, void *priv,
			    enum v4l2_buf_type i);
int tm6000_vidioc_reqbufs (struct file *file, void *priv,
			   struct v4l2_requestbuffers *rb);
int tm6000_vidioc_querybuf (struct file *file, void *priv,
			    struct v4l2_buffer *b);
int tm6000_vidioc_qbuf (struct file *file, void *priv, struct v4l2_buffer *b);
int tm6000_vidioc_dqbuf (struct file *file, void *priv, struct v4l2_buffer *b);
ssize_t tm6000_v4l2_read(struct file *filp, char __user * buf, size_t count,
			 loff_t * f_pos);
unsigned int tm6000_v4l2_poll(struct file *file,
			      struct poll_table_struct *wait);
int tm6000_queue_init(struct tm6000_core *dev);

/* In tm6000-alsa.c */
/*int tm6000_audio_init(struct tm6000_core *dev, int idx);*/


/* Debug stuff */

extern int tm6000_debug;

#define dprintk(dev, level, fmt, arg...) do {\
	if (tm6000_debug & level) \
		printk(KERN_INFO "(%lu) %s %s :"fmt, jiffies, 		\
			 dev->name, __FUNCTION__ , ##arg); } while (0)

#define V4L2_DEBUG_REG		0x0004
#define V4L2_DEBUG_I2C		0x0008
#define V4L2_DEBUG_QUEUE	0x0010
#define V4L2_DEBUG_ISOC		0x0020
#define V4L2_DEBUG_RES_LOCK	0x0040	/* Resource locking */
#define V4L2_DEBUG_OPEN		0x0080	/* video open/close debug */

#define tm6000_err(fmt, arg...) do {\
	printk(KERN_ERR "tm6000 %s :"fmt, \
		__FUNCTION__ , ##arg); } while (0)