blob: d2004965187bf54e47455a067881abf27f444950 [file] [log] [blame]
Mike Iselyd8554972006-06-26 20:58:46 -03001/*
2 *
3 * $Id$
4 *
5 * Copyright (C) 2005 Mike Isely <isely@pobox.com>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 *
20 */
21
22#include <linux/errno.h>
23#include <linux/string.h>
24#include <linux/slab.h>
25#include <linux/firmware.h>
Mike Iselyd8554972006-06-26 20:58:46 -030026#include <linux/videodev2.h>
Mike Isely32ffa9a2006-09-23 22:26:52 -030027#include <media/v4l2-common.h>
Mike Iselyb2bbaa92006-06-25 20:03:59 -030028#include <asm/semaphore.h>
Mike Iselyd8554972006-06-26 20:58:46 -030029#include "pvrusb2.h"
30#include "pvrusb2-std.h"
31#include "pvrusb2-util.h"
32#include "pvrusb2-hdw.h"
33#include "pvrusb2-i2c-core.h"
34#include "pvrusb2-tuner.h"
35#include "pvrusb2-eeprom.h"
36#include "pvrusb2-hdw-internal.h"
37#include "pvrusb2-encoder.h"
38#include "pvrusb2-debug.h"
39
40struct usb_device_id pvr2_device_table[] = {
41 [PVR2_HDW_TYPE_29XXX] = { USB_DEVICE(0x2040, 0x2900) },
Mike Iselyd8554972006-06-26 20:58:46 -030042 [PVR2_HDW_TYPE_24XXX] = { USB_DEVICE(0x2040, 0x2400) },
Mike Iselyd8554972006-06-26 20:58:46 -030043 { }
44};
45
46MODULE_DEVICE_TABLE(usb, pvr2_device_table);
47
48static const char *pvr2_device_names[] = {
49 [PVR2_HDW_TYPE_29XXX] = "WinTV PVR USB2 Model Category 29xxxx",
Mike Iselyd8554972006-06-26 20:58:46 -030050 [PVR2_HDW_TYPE_24XXX] = "WinTV PVR USB2 Model Category 24xxxx",
Mike Iselyd8554972006-06-26 20:58:46 -030051};
52
53struct pvr2_string_table {
54 const char **lst;
55 unsigned int cnt;
56};
57
Mike Iselyd8554972006-06-26 20:58:46 -030058// Names of other client modules to request for 24xxx model hardware
59static const char *pvr2_client_24xxx[] = {
60 "cx25840",
61 "tuner",
Mike Iselyd8554972006-06-26 20:58:46 -030062 "wm8775",
63};
Mike Iselyd8554972006-06-26 20:58:46 -030064
65// Names of other client modules to request for 29xxx model hardware
66static const char *pvr2_client_29xxx[] = {
67 "msp3400",
68 "saa7115",
69 "tuner",
Mike Iselyd8554972006-06-26 20:58:46 -030070};
71
72static struct pvr2_string_table pvr2_client_lists[] = {
73 [PVR2_HDW_TYPE_29XXX] = {
74 pvr2_client_29xxx,
75 sizeof(pvr2_client_29xxx)/sizeof(pvr2_client_29xxx[0]),
76 },
Mike Iselyd8554972006-06-26 20:58:46 -030077 [PVR2_HDW_TYPE_24XXX] = {
78 pvr2_client_24xxx,
79 sizeof(pvr2_client_24xxx)/sizeof(pvr2_client_24xxx[0]),
80 },
Mike Iselyd8554972006-06-26 20:58:46 -030081};
82
Mike Iselya0fd1cb2006-06-30 11:35:28 -030083static struct pvr2_hdw *unit_pointers[PVR_NUM] = {[ 0 ... PVR_NUM-1 ] = NULL};
Adrian Bunk07e337e2006-06-30 11:30:20 -030084static DECLARE_MUTEX(pvr2_unit_sem);
Mike Iselyd8554972006-06-26 20:58:46 -030085
86static int ctlchg = 0;
87static int initusbreset = 1;
88static int procreload = 0;
89static int tuner[PVR_NUM] = { [0 ... PVR_NUM-1] = -1 };
90static int tolerance[PVR_NUM] = { [0 ... PVR_NUM-1] = 0 };
91static int video_std[PVR_NUM] = { [0 ... PVR_NUM-1] = 0 };
92static int init_pause_msec = 0;
93
94module_param(ctlchg, int, S_IRUGO|S_IWUSR);
95MODULE_PARM_DESC(ctlchg, "0=optimize ctl change 1=always accept new ctl value");
96module_param(init_pause_msec, int, S_IRUGO|S_IWUSR);
97MODULE_PARM_DESC(init_pause_msec, "hardware initialization settling delay");
98module_param(initusbreset, int, S_IRUGO|S_IWUSR);
99MODULE_PARM_DESC(initusbreset, "Do USB reset device on probe");
100module_param(procreload, int, S_IRUGO|S_IWUSR);
101MODULE_PARM_DESC(procreload,
102 "Attempt init failure recovery with firmware reload");
103module_param_array(tuner, int, NULL, 0444);
104MODULE_PARM_DESC(tuner,"specify installed tuner type");
105module_param_array(video_std, int, NULL, 0444);
106MODULE_PARM_DESC(video_std,"specify initial video standard");
107module_param_array(tolerance, int, NULL, 0444);
108MODULE_PARM_DESC(tolerance,"specify stream error tolerance");
109
110#define PVR2_CTL_WRITE_ENDPOINT 0x01
111#define PVR2_CTL_READ_ENDPOINT 0x81
112
113#define PVR2_GPIO_IN 0x9008
114#define PVR2_GPIO_OUT 0x900c
115#define PVR2_GPIO_DIR 0x9020
116
117#define trace_firmware(...) pvr2_trace(PVR2_TRACE_FIRMWARE,__VA_ARGS__)
118
119#define PVR2_FIRMWARE_ENDPOINT 0x02
120
121/* size of a firmware chunk */
122#define FIRMWARE_CHUNK_SIZE 0x2000
123
Mike Iselyb30d2442006-06-25 20:05:01 -0300124/* Define the list of additional controls we'll dynamically construct based
125 on query of the cx2341x module. */
126struct pvr2_mpeg_ids {
127 const char *strid;
128 int id;
129};
130static const struct pvr2_mpeg_ids mpeg_ids[] = {
131 {
132 .strid = "audio_layer",
133 .id = V4L2_CID_MPEG_AUDIO_ENCODING,
134 },{
135 .strid = "audio_bitrate",
136 .id = V4L2_CID_MPEG_AUDIO_L2_BITRATE,
137 },{
138 /* Already using audio_mode elsewhere :-( */
139 .strid = "mpeg_audio_mode",
140 .id = V4L2_CID_MPEG_AUDIO_MODE,
141 },{
142 .strid = "mpeg_audio_mode_extension",
143 .id = V4L2_CID_MPEG_AUDIO_MODE_EXTENSION,
144 },{
145 .strid = "audio_emphasis",
146 .id = V4L2_CID_MPEG_AUDIO_EMPHASIS,
147 },{
148 .strid = "audio_crc",
149 .id = V4L2_CID_MPEG_AUDIO_CRC,
150 },{
151 .strid = "video_aspect",
152 .id = V4L2_CID_MPEG_VIDEO_ASPECT,
153 },{
154 .strid = "video_b_frames",
155 .id = V4L2_CID_MPEG_VIDEO_B_FRAMES,
156 },{
157 .strid = "video_gop_size",
158 .id = V4L2_CID_MPEG_VIDEO_GOP_SIZE,
159 },{
160 .strid = "video_gop_closure",
161 .id = V4L2_CID_MPEG_VIDEO_GOP_CLOSURE,
162 },{
163 .strid = "video_pulldown",
164 .id = V4L2_CID_MPEG_VIDEO_PULLDOWN,
165 },{
166 .strid = "video_bitrate_mode",
167 .id = V4L2_CID_MPEG_VIDEO_BITRATE_MODE,
168 },{
169 .strid = "video_bitrate",
170 .id = V4L2_CID_MPEG_VIDEO_BITRATE,
171 },{
172 .strid = "video_bitrate_peak",
173 .id = V4L2_CID_MPEG_VIDEO_BITRATE_PEAK,
174 },{
175 .strid = "video_temporal_decimation",
176 .id = V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION,
177 },{
178 .strid = "stream_type",
179 .id = V4L2_CID_MPEG_STREAM_TYPE,
180 },{
181 .strid = "video_spatial_filter_mode",
182 .id = V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE,
183 },{
184 .strid = "video_spatial_filter",
185 .id = V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER,
186 },{
187 .strid = "video_luma_spatial_filter_type",
188 .id = V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE,
189 },{
190 .strid = "video_chroma_spatial_filter_type",
191 .id = V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE,
192 },{
193 .strid = "video_temporal_filter_mode",
194 .id = V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE,
195 },{
196 .strid = "video_temporal_filter",
197 .id = V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER,
198 },{
199 .strid = "video_median_filter_type",
200 .id = V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE,
201 },{
202 .strid = "video_luma_median_filter_top",
203 .id = V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP,
204 },{
205 .strid = "video_luma_median_filter_bottom",
206 .id = V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM,
207 },{
208 .strid = "video_chroma_median_filter_top",
209 .id = V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP,
210 },{
211 .strid = "video_chroma_median_filter_bottom",
212 .id = V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM,
213 }
214};
215#define MPEGDEF_COUNT (sizeof(mpeg_ids)/sizeof(mpeg_ids[0]))
Mike Iselyc05c0462006-06-25 20:04:25 -0300216
Mike Iselyd8554972006-06-26 20:58:46 -0300217
Mike Isely434449f2006-08-08 09:10:06 -0300218static const char *control_values_srate[] = {
219 [V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100] = "44.1 kHz",
220 [V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000] = "48 kHz",
221 [V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000] = "32 kHz",
222};
Mike Iselyd8554972006-06-26 20:58:46 -0300223
Mike Iselyd8554972006-06-26 20:58:46 -0300224
225
226static const char *control_values_input[] = {
227 [PVR2_CVAL_INPUT_TV] = "television", /*xawtv needs this name*/
228 [PVR2_CVAL_INPUT_RADIO] = "radio",
229 [PVR2_CVAL_INPUT_SVIDEO] = "s-video",
230 [PVR2_CVAL_INPUT_COMPOSITE] = "composite",
231};
232
233
234static const char *control_values_audiomode[] = {
235 [V4L2_TUNER_MODE_MONO] = "Mono",
236 [V4L2_TUNER_MODE_STEREO] = "Stereo",
237 [V4L2_TUNER_MODE_LANG1] = "Lang1",
238 [V4L2_TUNER_MODE_LANG2] = "Lang2",
239 [V4L2_TUNER_MODE_LANG1_LANG2] = "Lang1+Lang2",
240};
241
242
243static const char *control_values_hsm[] = {
244 [PVR2_CVAL_HSM_FAIL] = "Fail",
245 [PVR2_CVAL_HSM_HIGH] = "High",
246 [PVR2_CVAL_HSM_FULL] = "Full",
247};
248
249
250static const char *control_values_subsystem[] = {
251 [PVR2_SUBSYS_B_ENC_FIRMWARE] = "enc_firmware",
252 [PVR2_SUBSYS_B_ENC_CFG] = "enc_config",
253 [PVR2_SUBSYS_B_DIGITIZER_RUN] = "digitizer_run",
254 [PVR2_SUBSYS_B_USBSTREAM_RUN] = "usbstream_run",
255 [PVR2_SUBSYS_B_ENC_RUN] = "enc_run",
256};
257
Adrian Bunk07e337e2006-06-30 11:30:20 -0300258static int pvr2_hdw_cmd_usbstream(struct pvr2_hdw *hdw,int runFl);
259static int pvr2_hdw_commit_ctl_internal(struct pvr2_hdw *hdw);
260static int pvr2_hdw_get_eeprom_addr(struct pvr2_hdw *hdw);
261static unsigned int pvr2_hdw_get_signal_status_internal(struct pvr2_hdw *hdw);
262static void pvr2_hdw_internal_find_stdenum(struct pvr2_hdw *hdw);
263static void pvr2_hdw_internal_set_std_avail(struct pvr2_hdw *hdw);
264static void pvr2_hdw_render_useless_unlocked(struct pvr2_hdw *hdw);
265static void pvr2_hdw_subsys_bit_chg_no_lock(struct pvr2_hdw *hdw,
266 unsigned long msk,
267 unsigned long val);
268static void pvr2_hdw_subsys_stream_bit_chg_no_lock(struct pvr2_hdw *hdw,
269 unsigned long msk,
270 unsigned long val);
271static int pvr2_send_request_ex(struct pvr2_hdw *hdw,
272 unsigned int timeout,int probe_fl,
273 void *write_data,unsigned int write_len,
274 void *read_data,unsigned int read_len);
275static int pvr2_write_u16(struct pvr2_hdw *hdw, u16 data, int res);
276static int pvr2_write_u8(struct pvr2_hdw *hdw, u8 data, int res);
Mike Iselyd8554972006-06-26 20:58:46 -0300277
278static int ctrl_channelfreq_get(struct pvr2_ctrl *cptr,int *vp)
279{
280 struct pvr2_hdw *hdw = cptr->hdw;
281 if ((hdw->freqProgSlot > 0) && (hdw->freqProgSlot <= FREQTABLE_SIZE)) {
282 *vp = hdw->freqTable[hdw->freqProgSlot-1];
283 } else {
284 *vp = 0;
285 }
286 return 0;
287}
288
289static int ctrl_channelfreq_set(struct pvr2_ctrl *cptr,int m,int v)
290{
291 struct pvr2_hdw *hdw = cptr->hdw;
292 if ((hdw->freqProgSlot > 0) && (hdw->freqProgSlot <= FREQTABLE_SIZE)) {
293 hdw->freqTable[hdw->freqProgSlot-1] = v;
294 }
295 return 0;
296}
297
298static int ctrl_channelprog_get(struct pvr2_ctrl *cptr,int *vp)
299{
300 *vp = cptr->hdw->freqProgSlot;
301 return 0;
302}
303
304static int ctrl_channelprog_set(struct pvr2_ctrl *cptr,int m,int v)
305{
306 struct pvr2_hdw *hdw = cptr->hdw;
307 if ((v >= 0) && (v <= FREQTABLE_SIZE)) {
308 hdw->freqProgSlot = v;
309 }
310 return 0;
311}
312
313static int ctrl_channel_get(struct pvr2_ctrl *cptr,int *vp)
314{
315 *vp = cptr->hdw->freqSlot;
316 return 0;
317}
318
319static int ctrl_channel_set(struct pvr2_ctrl *cptr,int m,int v)
320{
321 unsigned freq = 0;
322 struct pvr2_hdw *hdw = cptr->hdw;
323 hdw->freqSlot = v;
324 if ((hdw->freqSlot > 0) && (hdw->freqSlot <= FREQTABLE_SIZE)) {
325 freq = hdw->freqTable[hdw->freqSlot-1];
326 }
327 if (freq && (freq != hdw->freqVal)) {
328 hdw->freqVal = freq;
329 hdw->freqDirty = !0;
330 }
331 return 0;
332}
333
334static int ctrl_freq_get(struct pvr2_ctrl *cptr,int *vp)
335{
336 *vp = cptr->hdw->freqVal;
337 return 0;
338}
339
340static int ctrl_freq_is_dirty(struct pvr2_ctrl *cptr)
341{
342 return cptr->hdw->freqDirty != 0;
343}
344
345static void ctrl_freq_clear_dirty(struct pvr2_ctrl *cptr)
346{
347 cptr->hdw->freqDirty = 0;
348}
349
350static int ctrl_freq_set(struct pvr2_ctrl *cptr,int m,int v)
351{
352 struct pvr2_hdw *hdw = cptr->hdw;
353 hdw->freqVal = v;
354 hdw->freqDirty = !0;
355 hdw->freqSlot = 0;
356 return 0;
357}
358
Mike Isely3ad9fc32006-09-02 22:37:52 -0300359static int ctrl_vres_max_get(struct pvr2_ctrl *cptr,int *vp)
360{
361 /* Actual maximum depends on the video standard in effect. */
362 if (cptr->hdw->std_mask_cur & V4L2_STD_525_60) {
363 *vp = 480;
364 } else {
365 *vp = 576;
366 }
367 return 0;
368}
369
370static int ctrl_vres_min_get(struct pvr2_ctrl *cptr,int *vp)
371{
372 /* Actual minimum depends on device type. */
373 if (cptr->hdw->hdw_type == PVR2_HDW_TYPE_24XXX) {
374 *vp = 75;
375 } else {
376 *vp = 17;
377 }
378 return 0;
379}
380
Mike Iselyb30d2442006-06-25 20:05:01 -0300381static int ctrl_cx2341x_is_dirty(struct pvr2_ctrl *cptr)
382{
383 return cptr->hdw->enc_stale != 0;
384}
385
386static void ctrl_cx2341x_clear_dirty(struct pvr2_ctrl *cptr)
387{
388 cptr->hdw->enc_stale = 0;
389}
390
391static int ctrl_cx2341x_get(struct pvr2_ctrl *cptr,int *vp)
392{
393 int ret;
394 struct v4l2_ext_controls cs;
395 struct v4l2_ext_control c1;
396 memset(&cs,0,sizeof(cs));
397 memset(&c1,0,sizeof(c1));
398 cs.controls = &c1;
399 cs.count = 1;
400 c1.id = cptr->info->v4l_id;
401 ret = cx2341x_ext_ctrls(&cptr->hdw->enc_ctl_state,&cs,
402 VIDIOC_G_EXT_CTRLS);
403 if (ret) return ret;
404 *vp = c1.value;
405 return 0;
406}
407
408static int ctrl_cx2341x_set(struct pvr2_ctrl *cptr,int m,int v)
409{
410 int ret;
411 struct v4l2_ext_controls cs;
412 struct v4l2_ext_control c1;
413 memset(&cs,0,sizeof(cs));
414 memset(&c1,0,sizeof(c1));
415 cs.controls = &c1;
416 cs.count = 1;
417 c1.id = cptr->info->v4l_id;
418 c1.value = v;
419 ret = cx2341x_ext_ctrls(&cptr->hdw->enc_ctl_state,&cs,
420 VIDIOC_S_EXT_CTRLS);
421 if (ret) return ret;
422 cptr->hdw->enc_stale = !0;
423 return 0;
424}
425
426static unsigned int ctrl_cx2341x_getv4lflags(struct pvr2_ctrl *cptr)
427{
428 struct v4l2_queryctrl qctrl;
429 struct pvr2_ctl_info *info;
430 qctrl.id = cptr->info->v4l_id;
431 cx2341x_ctrl_query(&cptr->hdw->enc_ctl_state,&qctrl);
432 /* Strip out the const so we can adjust a function pointer. It's
433 OK to do this here because we know this is a dynamically created
434 control, so the underlying storage for the info pointer is (a)
435 private to us, and (b) not in read-only storage. Either we do
436 this or we significantly complicate the underlying control
437 implementation. */
438 info = (struct pvr2_ctl_info *)(cptr->info);
439 if (qctrl.flags & V4L2_CTRL_FLAG_READ_ONLY) {
440 if (info->set_value) {
Mike Iselya0fd1cb2006-06-30 11:35:28 -0300441 info->set_value = NULL;
Mike Iselyb30d2442006-06-25 20:05:01 -0300442 }
443 } else {
444 if (!(info->set_value)) {
445 info->set_value = ctrl_cx2341x_set;
446 }
447 }
448 return qctrl.flags;
449}
450
Mike Iselyd8554972006-06-26 20:58:46 -0300451static int ctrl_streamingenabled_get(struct pvr2_ctrl *cptr,int *vp)
452{
453 *vp = cptr->hdw->flag_streaming_enabled;
454 return 0;
455}
456
457static int ctrl_hsm_get(struct pvr2_ctrl *cptr,int *vp)
458{
459 int result = pvr2_hdw_is_hsm(cptr->hdw);
460 *vp = PVR2_CVAL_HSM_FULL;
461 if (result < 0) *vp = PVR2_CVAL_HSM_FAIL;
462 if (result) *vp = PVR2_CVAL_HSM_HIGH;
463 return 0;
464}
465
466static int ctrl_stdavail_get(struct pvr2_ctrl *cptr,int *vp)
467{
468 *vp = cptr->hdw->std_mask_avail;
469 return 0;
470}
471
472static int ctrl_stdavail_set(struct pvr2_ctrl *cptr,int m,int v)
473{
474 struct pvr2_hdw *hdw = cptr->hdw;
475 v4l2_std_id ns;
476 ns = hdw->std_mask_avail;
477 ns = (ns & ~m) | (v & m);
478 if (ns == hdw->std_mask_avail) return 0;
479 hdw->std_mask_avail = ns;
480 pvr2_hdw_internal_set_std_avail(hdw);
481 pvr2_hdw_internal_find_stdenum(hdw);
482 return 0;
483}
484
485static int ctrl_std_val_to_sym(struct pvr2_ctrl *cptr,int msk,int val,
486 char *bufPtr,unsigned int bufSize,
487 unsigned int *len)
488{
489 *len = pvr2_std_id_to_str(bufPtr,bufSize,msk & val);
490 return 0;
491}
492
493static int ctrl_std_sym_to_val(struct pvr2_ctrl *cptr,
494 const char *bufPtr,unsigned int bufSize,
495 int *mskp,int *valp)
496{
497 int ret;
498 v4l2_std_id id;
499 ret = pvr2_std_str_to_id(&id,bufPtr,bufSize);
500 if (ret < 0) return ret;
501 if (mskp) *mskp = id;
502 if (valp) *valp = id;
503 return 0;
504}
505
506static int ctrl_stdcur_get(struct pvr2_ctrl *cptr,int *vp)
507{
508 *vp = cptr->hdw->std_mask_cur;
509 return 0;
510}
511
512static int ctrl_stdcur_set(struct pvr2_ctrl *cptr,int m,int v)
513{
514 struct pvr2_hdw *hdw = cptr->hdw;
515 v4l2_std_id ns;
516 ns = hdw->std_mask_cur;
517 ns = (ns & ~m) | (v & m);
518 if (ns == hdw->std_mask_cur) return 0;
519 hdw->std_mask_cur = ns;
520 hdw->std_dirty = !0;
521 pvr2_hdw_internal_find_stdenum(hdw);
522 return 0;
523}
524
525static int ctrl_stdcur_is_dirty(struct pvr2_ctrl *cptr)
526{
527 return cptr->hdw->std_dirty != 0;
528}
529
530static void ctrl_stdcur_clear_dirty(struct pvr2_ctrl *cptr)
531{
532 cptr->hdw->std_dirty = 0;
533}
534
535static int ctrl_signal_get(struct pvr2_ctrl *cptr,int *vp)
536{
537 *vp = ((pvr2_hdw_get_signal_status_internal(cptr->hdw) &
538 PVR2_SIGNAL_OK) ? 1 : 0);
539 return 0;
540}
541
542static int ctrl_subsys_get(struct pvr2_ctrl *cptr,int *vp)
543{
544 *vp = cptr->hdw->subsys_enabled_mask;
545 return 0;
546}
547
548static int ctrl_subsys_set(struct pvr2_ctrl *cptr,int m,int v)
549{
550 pvr2_hdw_subsys_bit_chg_no_lock(cptr->hdw,m,v);
551 return 0;
552}
553
554static int ctrl_subsys_stream_get(struct pvr2_ctrl *cptr,int *vp)
555{
556 *vp = cptr->hdw->subsys_stream_mask;
557 return 0;
558}
559
560static int ctrl_subsys_stream_set(struct pvr2_ctrl *cptr,int m,int v)
561{
562 pvr2_hdw_subsys_stream_bit_chg_no_lock(cptr->hdw,m,v);
563 return 0;
564}
565
566static int ctrl_stdenumcur_set(struct pvr2_ctrl *cptr,int m,int v)
567{
568 struct pvr2_hdw *hdw = cptr->hdw;
569 if (v < 0) return -EINVAL;
570 if (v > hdw->std_enum_cnt) return -EINVAL;
571 hdw->std_enum_cur = v;
572 if (!v) return 0;
573 v--;
574 if (hdw->std_mask_cur == hdw->std_defs[v].id) return 0;
575 hdw->std_mask_cur = hdw->std_defs[v].id;
576 hdw->std_dirty = !0;
577 return 0;
578}
579
580
581static int ctrl_stdenumcur_get(struct pvr2_ctrl *cptr,int *vp)
582{
583 *vp = cptr->hdw->std_enum_cur;
584 return 0;
585}
586
587
588static int ctrl_stdenumcur_is_dirty(struct pvr2_ctrl *cptr)
589{
590 return cptr->hdw->std_dirty != 0;
591}
592
593
594static void ctrl_stdenumcur_clear_dirty(struct pvr2_ctrl *cptr)
595{
596 cptr->hdw->std_dirty = 0;
597}
598
599
600#define DEFINT(vmin,vmax) \
601 .type = pvr2_ctl_int, \
602 .def.type_int.min_value = vmin, \
603 .def.type_int.max_value = vmax
604
605#define DEFENUM(tab) \
606 .type = pvr2_ctl_enum, \
607 .def.type_enum.count = (sizeof(tab)/sizeof((tab)[0])), \
608 .def.type_enum.value_names = tab
609
Mike Isely33213962006-06-25 20:04:40 -0300610#define DEFBOOL \
611 .type = pvr2_ctl_bool
612
Mike Iselyd8554972006-06-26 20:58:46 -0300613#define DEFMASK(msk,tab) \
614 .type = pvr2_ctl_bitmask, \
615 .def.type_bitmask.valid_bits = msk, \
616 .def.type_bitmask.bit_names = tab
617
618#define DEFREF(vname) \
619 .set_value = ctrl_set_##vname, \
620 .get_value = ctrl_get_##vname, \
621 .is_dirty = ctrl_isdirty_##vname, \
622 .clear_dirty = ctrl_cleardirty_##vname
623
624
625#define VCREATE_FUNCS(vname) \
626static int ctrl_get_##vname(struct pvr2_ctrl *cptr,int *vp) \
627{*vp = cptr->hdw->vname##_val; return 0;} \
628static int ctrl_set_##vname(struct pvr2_ctrl *cptr,int m,int v) \
629{cptr->hdw->vname##_val = v; cptr->hdw->vname##_dirty = !0; return 0;} \
630static int ctrl_isdirty_##vname(struct pvr2_ctrl *cptr) \
631{return cptr->hdw->vname##_dirty != 0;} \
632static void ctrl_cleardirty_##vname(struct pvr2_ctrl *cptr) \
633{cptr->hdw->vname##_dirty = 0;}
634
635VCREATE_FUNCS(brightness)
636VCREATE_FUNCS(contrast)
637VCREATE_FUNCS(saturation)
638VCREATE_FUNCS(hue)
639VCREATE_FUNCS(volume)
640VCREATE_FUNCS(balance)
641VCREATE_FUNCS(bass)
642VCREATE_FUNCS(treble)
643VCREATE_FUNCS(mute)
Mike Iselyc05c0462006-06-25 20:04:25 -0300644VCREATE_FUNCS(input)
645VCREATE_FUNCS(audiomode)
646VCREATE_FUNCS(res_hor)
647VCREATE_FUNCS(res_ver)
Mike Iselyd8554972006-06-26 20:58:46 -0300648VCREATE_FUNCS(srate)
Mike Iselyd8554972006-06-26 20:58:46 -0300649
650#define MIN_FREQ 55250000L
651#define MAX_FREQ 850000000L
652
653/* Table definition of all controls which can be manipulated */
654static const struct pvr2_ctl_info control_defs[] = {
655 {
656 .v4l_id = V4L2_CID_BRIGHTNESS,
657 .desc = "Brightness",
658 .name = "brightness",
659 .default_value = 128,
660 DEFREF(brightness),
661 DEFINT(0,255),
662 },{
663 .v4l_id = V4L2_CID_CONTRAST,
664 .desc = "Contrast",
665 .name = "contrast",
666 .default_value = 68,
667 DEFREF(contrast),
668 DEFINT(0,127),
669 },{
670 .v4l_id = V4L2_CID_SATURATION,
671 .desc = "Saturation",
672 .name = "saturation",
673 .default_value = 64,
674 DEFREF(saturation),
675 DEFINT(0,127),
676 },{
677 .v4l_id = V4L2_CID_HUE,
678 .desc = "Hue",
679 .name = "hue",
680 .default_value = 0,
681 DEFREF(hue),
682 DEFINT(-128,127),
683 },{
684 .v4l_id = V4L2_CID_AUDIO_VOLUME,
685 .desc = "Volume",
686 .name = "volume",
687 .default_value = 65535,
688 DEFREF(volume),
689 DEFINT(0,65535),
690 },{
691 .v4l_id = V4L2_CID_AUDIO_BALANCE,
692 .desc = "Balance",
693 .name = "balance",
694 .default_value = 0,
695 DEFREF(balance),
696 DEFINT(-32768,32767),
697 },{
698 .v4l_id = V4L2_CID_AUDIO_BASS,
699 .desc = "Bass",
700 .name = "bass",
701 .default_value = 0,
702 DEFREF(bass),
703 DEFINT(-32768,32767),
704 },{
705 .v4l_id = V4L2_CID_AUDIO_TREBLE,
706 .desc = "Treble",
707 .name = "treble",
708 .default_value = 0,
709 DEFREF(treble),
710 DEFINT(-32768,32767),
711 },{
712 .v4l_id = V4L2_CID_AUDIO_MUTE,
713 .desc = "Mute",
714 .name = "mute",
715 .default_value = 0,
716 DEFREF(mute),
Mike Isely33213962006-06-25 20:04:40 -0300717 DEFBOOL,
Mike Iselyd8554972006-06-26 20:58:46 -0300718 },{
Mike Iselyc05c0462006-06-25 20:04:25 -0300719 .desc = "Video Source",
720 .name = "input",
721 .internal_id = PVR2_CID_INPUT,
722 .default_value = PVR2_CVAL_INPUT_TV,
723 DEFREF(input),
724 DEFENUM(control_values_input),
725 },{
726 .desc = "Audio Mode",
727 .name = "audio_mode",
728 .internal_id = PVR2_CID_AUDIOMODE,
729 .default_value = V4L2_TUNER_MODE_STEREO,
730 DEFREF(audiomode),
731 DEFENUM(control_values_audiomode),
732 },{
733 .desc = "Horizontal capture resolution",
734 .name = "resolution_hor",
735 .internal_id = PVR2_CID_HRES,
736 .default_value = 720,
737 DEFREF(res_hor),
Mike Isely3ad9fc32006-09-02 22:37:52 -0300738 DEFINT(19,720),
Mike Iselyc05c0462006-06-25 20:04:25 -0300739 },{
740 .desc = "Vertical capture resolution",
741 .name = "resolution_ver",
742 .internal_id = PVR2_CID_VRES,
743 .default_value = 480,
744 DEFREF(res_ver),
Mike Isely3ad9fc32006-09-02 22:37:52 -0300745 DEFINT(17,576),
746 /* Hook in check for video standard and adjust maximum
747 depending on the standard. */
748 .get_max_value = ctrl_vres_max_get,
749 .get_min_value = ctrl_vres_min_get,
Mike Iselyc05c0462006-06-25 20:04:25 -0300750 },{
Mike Iselyb30d2442006-06-25 20:05:01 -0300751 .v4l_id = V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ,
Mike Isely434449f2006-08-08 09:10:06 -0300752 .default_value = V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000,
753 .desc = "Audio Sampling Frequency",
Mike Iselyd8554972006-06-26 20:58:46 -0300754 .name = "srate",
Mike Iselyd8554972006-06-26 20:58:46 -0300755 DEFREF(srate),
756 DEFENUM(control_values_srate),
757 },{
Mike Iselyd8554972006-06-26 20:58:46 -0300758 .desc = "Tuner Frequency (Hz)",
759 .name = "frequency",
760 .internal_id = PVR2_CID_FREQUENCY,
761 .default_value = 175250000L,
762 .set_value = ctrl_freq_set,
763 .get_value = ctrl_freq_get,
764 .is_dirty = ctrl_freq_is_dirty,
765 .clear_dirty = ctrl_freq_clear_dirty,
766 DEFINT(MIN_FREQ,MAX_FREQ),
767 },{
768 .desc = "Channel",
769 .name = "channel",
770 .set_value = ctrl_channel_set,
771 .get_value = ctrl_channel_get,
772 DEFINT(0,FREQTABLE_SIZE),
773 },{
774 .desc = "Channel Program Frequency",
775 .name = "freq_table_value",
776 .set_value = ctrl_channelfreq_set,
777 .get_value = ctrl_channelfreq_get,
778 DEFINT(MIN_FREQ,MAX_FREQ),
779 },{
780 .desc = "Channel Program ID",
781 .name = "freq_table_channel",
782 .set_value = ctrl_channelprog_set,
783 .get_value = ctrl_channelprog_get,
784 DEFINT(0,FREQTABLE_SIZE),
785 },{
Mike Iselyd8554972006-06-26 20:58:46 -0300786 .desc = "Streaming Enabled",
787 .name = "streaming_enabled",
788 .get_value = ctrl_streamingenabled_get,
Mike Isely33213962006-06-25 20:04:40 -0300789 DEFBOOL,
Mike Iselyd8554972006-06-26 20:58:46 -0300790 },{
791 .desc = "USB Speed",
792 .name = "usb_speed",
793 .get_value = ctrl_hsm_get,
794 DEFENUM(control_values_hsm),
795 },{
796 .desc = "Signal Present",
797 .name = "signal_present",
798 .get_value = ctrl_signal_get,
Mike Isely33213962006-06-25 20:04:40 -0300799 DEFBOOL,
Mike Iselyd8554972006-06-26 20:58:46 -0300800 },{
801 .desc = "Video Standards Available Mask",
802 .name = "video_standard_mask_available",
803 .internal_id = PVR2_CID_STDAVAIL,
804 .skip_init = !0,
805 .get_value = ctrl_stdavail_get,
806 .set_value = ctrl_stdavail_set,
807 .val_to_sym = ctrl_std_val_to_sym,
808 .sym_to_val = ctrl_std_sym_to_val,
809 .type = pvr2_ctl_bitmask,
810 },{
811 .desc = "Video Standards In Use Mask",
812 .name = "video_standard_mask_active",
813 .internal_id = PVR2_CID_STDCUR,
814 .skip_init = !0,
815 .get_value = ctrl_stdcur_get,
816 .set_value = ctrl_stdcur_set,
817 .is_dirty = ctrl_stdcur_is_dirty,
818 .clear_dirty = ctrl_stdcur_clear_dirty,
819 .val_to_sym = ctrl_std_val_to_sym,
820 .sym_to_val = ctrl_std_sym_to_val,
821 .type = pvr2_ctl_bitmask,
822 },{
823 .desc = "Subsystem enabled mask",
824 .name = "debug_subsys_mask",
825 .skip_init = !0,
826 .get_value = ctrl_subsys_get,
827 .set_value = ctrl_subsys_set,
828 DEFMASK(PVR2_SUBSYS_ALL,control_values_subsystem),
829 },{
830 .desc = "Subsystem stream mask",
831 .name = "debug_subsys_stream_mask",
832 .skip_init = !0,
833 .get_value = ctrl_subsys_stream_get,
834 .set_value = ctrl_subsys_stream_set,
835 DEFMASK(PVR2_SUBSYS_ALL,control_values_subsystem),
836 },{
837 .desc = "Video Standard Name",
838 .name = "video_standard",
839 .internal_id = PVR2_CID_STDENUM,
840 .skip_init = !0,
841 .get_value = ctrl_stdenumcur_get,
842 .set_value = ctrl_stdenumcur_set,
843 .is_dirty = ctrl_stdenumcur_is_dirty,
844 .clear_dirty = ctrl_stdenumcur_clear_dirty,
845 .type = pvr2_ctl_enum,
846 }
847};
848
Mike Iselyc05c0462006-06-25 20:04:25 -0300849#define CTRLDEF_COUNT (sizeof(control_defs)/sizeof(control_defs[0]))
Mike Iselyd8554972006-06-26 20:58:46 -0300850
851
852const char *pvr2_config_get_name(enum pvr2_config cfg)
853{
854 switch (cfg) {
855 case pvr2_config_empty: return "empty";
856 case pvr2_config_mpeg: return "mpeg";
857 case pvr2_config_vbi: return "vbi";
858 case pvr2_config_radio: return "radio";
859 }
860 return "<unknown>";
861}
862
863
864struct usb_device *pvr2_hdw_get_dev(struct pvr2_hdw *hdw)
865{
866 return hdw->usb_dev;
867}
868
869
870unsigned long pvr2_hdw_get_sn(struct pvr2_hdw *hdw)
871{
872 return hdw->serial_number;
873}
874
Mike Iselyd8554972006-06-26 20:58:46 -0300875int pvr2_hdw_get_unit_number(struct pvr2_hdw *hdw)
876{
877 return hdw->unit_number;
878}
879
880
881/* Attempt to locate one of the given set of files. Messages are logged
882 appropriate to what has been found. The return value will be 0 or
883 greater on success (it will be the index of the file name found) and
884 fw_entry will be filled in. Otherwise a negative error is returned on
885 failure. If the return value is -ENOENT then no viable firmware file
886 could be located. */
887static int pvr2_locate_firmware(struct pvr2_hdw *hdw,
888 const struct firmware **fw_entry,
889 const char *fwtypename,
890 unsigned int fwcount,
891 const char *fwnames[])
892{
893 unsigned int idx;
894 int ret = -EINVAL;
895 for (idx = 0; idx < fwcount; idx++) {
896 ret = request_firmware(fw_entry,
897 fwnames[idx],
898 &hdw->usb_dev->dev);
899 if (!ret) {
900 trace_firmware("Located %s firmware: %s;"
901 " uploading...",
902 fwtypename,
903 fwnames[idx]);
904 return idx;
905 }
906 if (ret == -ENOENT) continue;
907 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
908 "request_firmware fatal error with code=%d",ret);
909 return ret;
910 }
911 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
912 "***WARNING***"
913 " Device %s firmware"
914 " seems to be missing.",
915 fwtypename);
916 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
917 "Did you install the pvrusb2 firmware files"
918 " in their proper location?");
919 if (fwcount == 1) {
920 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
921 "request_firmware unable to locate %s file %s",
922 fwtypename,fwnames[0]);
923 } else {
924 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
925 "request_firmware unable to locate"
926 " one of the following %s files:",
927 fwtypename);
928 for (idx = 0; idx < fwcount; idx++) {
929 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
930 "request_firmware: Failed to find %s",
931 fwnames[idx]);
932 }
933 }
934 return ret;
935}
936
937
938/*
939 * pvr2_upload_firmware1().
940 *
941 * Send the 8051 firmware to the device. After the upload, arrange for
942 * device to re-enumerate.
943 *
944 * NOTE : the pointer to the firmware data given by request_firmware()
945 * is not suitable for an usb transaction.
946 *
947 */
Adrian Bunk07e337e2006-06-30 11:30:20 -0300948static int pvr2_upload_firmware1(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -0300949{
Mike Iselya0fd1cb2006-06-30 11:35:28 -0300950 const struct firmware *fw_entry = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -0300951 void *fw_ptr;
952 unsigned int pipe;
953 int ret;
954 u16 address;
955 static const char *fw_files_29xxx[] = {
956 "v4l-pvrusb2-29xxx-01.fw",
957 };
Mike Iselyd8554972006-06-26 20:58:46 -0300958 static const char *fw_files_24xxx[] = {
959 "v4l-pvrusb2-24xxx-01.fw",
960 };
Mike Iselyd8554972006-06-26 20:58:46 -0300961 static const struct pvr2_string_table fw_file_defs[] = {
962 [PVR2_HDW_TYPE_29XXX] = {
963 fw_files_29xxx,
964 sizeof(fw_files_29xxx)/sizeof(fw_files_29xxx[0]),
965 },
Mike Iselyd8554972006-06-26 20:58:46 -0300966 [PVR2_HDW_TYPE_24XXX] = {
967 fw_files_24xxx,
968 sizeof(fw_files_24xxx)/sizeof(fw_files_24xxx[0]),
969 },
Mike Iselyd8554972006-06-26 20:58:46 -0300970 };
971 hdw->fw1_state = FW1_STATE_FAILED; // default result
972
973 trace_firmware("pvr2_upload_firmware1");
974
975 ret = pvr2_locate_firmware(hdw,&fw_entry,"fx2 controller",
976 fw_file_defs[hdw->hdw_type].cnt,
977 fw_file_defs[hdw->hdw_type].lst);
978 if (ret < 0) {
979 if (ret == -ENOENT) hdw->fw1_state = FW1_STATE_MISSING;
980 return ret;
981 }
982
983 usb_settoggle(hdw->usb_dev, 0 & 0xf, !(0 & USB_DIR_IN), 0);
984 usb_clear_halt(hdw->usb_dev, usb_sndbulkpipe(hdw->usb_dev, 0 & 0x7f));
985
986 pipe = usb_sndctrlpipe(hdw->usb_dev, 0);
987
988 if (fw_entry->size != 0x2000){
989 pvr2_trace(PVR2_TRACE_ERROR_LEGS,"wrong fx2 firmware size");
990 release_firmware(fw_entry);
991 return -ENOMEM;
992 }
993
994 fw_ptr = kmalloc(0x800, GFP_KERNEL);
995 if (fw_ptr == NULL){
996 release_firmware(fw_entry);
997 return -ENOMEM;
998 }
999
1000 /* We have to hold the CPU during firmware upload. */
1001 pvr2_hdw_cpureset_assert(hdw,1);
1002
1003 /* upload the firmware to address 0000-1fff in 2048 (=0x800) bytes
1004 chunk. */
1005
1006 ret = 0;
1007 for(address = 0; address < fw_entry->size; address += 0x800) {
1008 memcpy(fw_ptr, fw_entry->data + address, 0x800);
1009 ret += usb_control_msg(hdw->usb_dev, pipe, 0xa0, 0x40, address,
1010 0, fw_ptr, 0x800, HZ);
1011 }
1012
1013 trace_firmware("Upload done, releasing device's CPU");
1014
1015 /* Now release the CPU. It will disconnect and reconnect later. */
1016 pvr2_hdw_cpureset_assert(hdw,0);
1017
1018 kfree(fw_ptr);
1019 release_firmware(fw_entry);
1020
1021 trace_firmware("Upload done (%d bytes sent)",ret);
1022
1023 /* We should have written 8192 bytes */
1024 if (ret == 8192) {
1025 hdw->fw1_state = FW1_STATE_RELOAD;
1026 return 0;
1027 }
1028
1029 return -EIO;
1030}
1031
1032
1033/*
1034 * pvr2_upload_firmware2()
1035 *
1036 * This uploads encoder firmware on endpoint 2.
1037 *
1038 */
1039
1040int pvr2_upload_firmware2(struct pvr2_hdw *hdw)
1041{
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001042 const struct firmware *fw_entry = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001043 void *fw_ptr;
1044 unsigned int pipe, fw_len, fw_done;
1045 int actual_length;
1046 int ret = 0;
1047 int fwidx;
1048 static const char *fw_files[] = {
1049 CX2341X_FIRM_ENC_FILENAME,
1050 };
1051
1052 trace_firmware("pvr2_upload_firmware2");
1053
1054 ret = pvr2_locate_firmware(hdw,&fw_entry,"encoder",
1055 sizeof(fw_files)/sizeof(fw_files[0]),
1056 fw_files);
1057 if (ret < 0) return ret;
1058 fwidx = ret;
1059 ret = 0;
Mike Iselyb30d2442006-06-25 20:05:01 -03001060 /* Since we're about to completely reinitialize the encoder,
1061 invalidate our cached copy of its configuration state. Next
1062 time we configure the encoder, then we'll fully configure it. */
1063 hdw->enc_cur_valid = 0;
Mike Iselyd8554972006-06-26 20:58:46 -03001064
1065 /* First prepare firmware loading */
1066 ret |= pvr2_write_register(hdw, 0x0048, 0xffffffff); /*interrupt mask*/
1067 ret |= pvr2_hdw_gpio_chg_dir(hdw,0xffffffff,0x00000088); /*gpio dir*/
1068 ret |= pvr2_hdw_gpio_chg_out(hdw,0xffffffff,0x00000008); /*gpio output state*/
1069 ret |= pvr2_hdw_cmd_deep_reset(hdw);
1070 ret |= pvr2_write_register(hdw, 0xa064, 0x00000000); /*APU command*/
1071 ret |= pvr2_hdw_gpio_chg_dir(hdw,0xffffffff,0x00000408); /*gpio dir*/
1072 ret |= pvr2_hdw_gpio_chg_out(hdw,0xffffffff,0x00000008); /*gpio output state*/
1073 ret |= pvr2_write_register(hdw, 0x9058, 0xffffffed); /*VPU ctrl*/
1074 ret |= pvr2_write_register(hdw, 0x9054, 0xfffffffd); /*reset hw blocks*/
1075 ret |= pvr2_write_register(hdw, 0x07f8, 0x80000800); /*encoder SDRAM refresh*/
1076 ret |= pvr2_write_register(hdw, 0x07fc, 0x0000001a); /*encoder SDRAM pre-charge*/
1077 ret |= pvr2_write_register(hdw, 0x0700, 0x00000000); /*I2C clock*/
1078 ret |= pvr2_write_register(hdw, 0xaa00, 0x00000000); /*unknown*/
1079 ret |= pvr2_write_register(hdw, 0xaa04, 0x00057810); /*unknown*/
1080 ret |= pvr2_write_register(hdw, 0xaa10, 0x00148500); /*unknown*/
1081 ret |= pvr2_write_register(hdw, 0xaa18, 0x00840000); /*unknown*/
1082 ret |= pvr2_write_u8(hdw, 0x52, 0);
1083 ret |= pvr2_write_u16(hdw, 0x0600, 0);
1084
1085 if (ret) {
1086 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1087 "firmware2 upload prep failed, ret=%d",ret);
1088 release_firmware(fw_entry);
1089 return ret;
1090 }
1091
1092 /* Now send firmware */
1093
1094 fw_len = fw_entry->size;
1095
1096 if (fw_len % FIRMWARE_CHUNK_SIZE) {
1097 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1098 "size of %s firmware"
1099 " must be a multiple of 8192B",
1100 fw_files[fwidx]);
1101 release_firmware(fw_entry);
1102 return -1;
1103 }
1104
1105 fw_ptr = kmalloc(FIRMWARE_CHUNK_SIZE, GFP_KERNEL);
1106 if (fw_ptr == NULL){
1107 release_firmware(fw_entry);
1108 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1109 "failed to allocate memory for firmware2 upload");
1110 return -ENOMEM;
1111 }
1112
1113 pipe = usb_sndbulkpipe(hdw->usb_dev, PVR2_FIRMWARE_ENDPOINT);
1114
1115 for (fw_done = 0 ; (fw_done < fw_len) && !ret ;
1116 fw_done += FIRMWARE_CHUNK_SIZE ) {
1117 int i;
1118 memcpy(fw_ptr, fw_entry->data + fw_done, FIRMWARE_CHUNK_SIZE);
1119 /* Usbsnoop log shows that we must swap bytes... */
1120 for (i = 0; i < FIRMWARE_CHUNK_SIZE/4 ; i++)
1121 ((u32 *)fw_ptr)[i] = ___swab32(((u32 *)fw_ptr)[i]);
1122
1123 ret |= usb_bulk_msg(hdw->usb_dev, pipe, fw_ptr,
1124 FIRMWARE_CHUNK_SIZE,
1125 &actual_length, HZ);
1126 ret |= (actual_length != FIRMWARE_CHUNK_SIZE);
1127 }
1128
1129 trace_firmware("upload of %s : %i / %i ",
1130 fw_files[fwidx],fw_done,fw_len);
1131
1132 kfree(fw_ptr);
1133 release_firmware(fw_entry);
1134
1135 if (ret) {
1136 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1137 "firmware2 upload transfer failure");
1138 return ret;
1139 }
1140
1141 /* Finish upload */
1142
1143 ret |= pvr2_write_register(hdw, 0x9054, 0xffffffff); /*reset hw blocks*/
1144 ret |= pvr2_write_register(hdw, 0x9058, 0xffffffe8); /*VPU ctrl*/
1145 ret |= pvr2_write_u16(hdw, 0x0600, 0);
1146
1147 if (ret) {
1148 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1149 "firmware2 upload post-proc failure");
1150 } else {
1151 hdw->subsys_enabled_mask |= (1<<PVR2_SUBSYS_B_ENC_FIRMWARE);
1152 }
1153 return ret;
1154}
1155
1156
1157#define FIRMWARE_RECOVERY_BITS \
1158 ((1<<PVR2_SUBSYS_B_ENC_CFG) | \
1159 (1<<PVR2_SUBSYS_B_ENC_RUN) | \
1160 (1<<PVR2_SUBSYS_B_ENC_FIRMWARE) | \
1161 (1<<PVR2_SUBSYS_B_USBSTREAM_RUN))
1162
1163/*
1164
1165 This single function is key to pretty much everything. The pvrusb2
1166 device can logically be viewed as a series of subsystems which can be
1167 stopped / started or unconfigured / configured. To get things streaming,
1168 one must configure everything and start everything, but there may be
1169 various reasons over time to deconfigure something or stop something.
1170 This function handles all of this activity. Everything EVERYWHERE that
1171 must affect a subsystem eventually comes here to do the work.
1172
1173 The current state of all subsystems is represented by a single bit mask,
1174 known as subsys_enabled_mask. The bit positions are defined by the
1175 PVR2_SUBSYS_xxxx macros, with one subsystem per bit position. At any
1176 time the set of configured or active subsystems can be queried just by
1177 looking at that mask. To change bits in that mask, this function here
1178 must be called. The "msk" argument indicates which bit positions to
1179 change, and the "val" argument defines the new values for the positions
1180 defined by "msk".
1181
1182 There is a priority ordering of starting / stopping things, and for
1183 multiple requested changes, this function implements that ordering.
1184 (Thus we will act on a request to load encoder firmware before we
1185 configure the encoder.) In addition to priority ordering, there is a
1186 recovery strategy implemented here. If a particular step fails and we
1187 detect that failure, this function will clear the affected subsystem bits
1188 and restart. Thus we have a means for recovering from a dead encoder:
1189 Clear all bits that correspond to subsystems that we need to restart /
1190 reconfigure and start over.
1191
1192*/
Adrian Bunk07e337e2006-06-30 11:30:20 -03001193static void pvr2_hdw_subsys_bit_chg_no_lock(struct pvr2_hdw *hdw,
1194 unsigned long msk,
1195 unsigned long val)
Mike Iselyd8554972006-06-26 20:58:46 -03001196{
1197 unsigned long nmsk;
1198 unsigned long vmsk;
1199 int ret;
1200 unsigned int tryCount = 0;
1201
1202 if (!hdw->flag_ok) return;
1203
1204 msk &= PVR2_SUBSYS_ALL;
Mike Iselyeb8e0ee2006-06-25 20:04:47 -03001205 nmsk = (hdw->subsys_enabled_mask & ~msk) | (val & msk);
1206 nmsk &= PVR2_SUBSYS_ALL;
Mike Iselyd8554972006-06-26 20:58:46 -03001207
1208 for (;;) {
1209 tryCount++;
Mike Iselyeb8e0ee2006-06-25 20:04:47 -03001210 if (!((nmsk ^ hdw->subsys_enabled_mask) &
1211 PVR2_SUBSYS_ALL)) break;
Mike Iselyd8554972006-06-26 20:58:46 -03001212 if (tryCount > 4) {
1213 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1214 "Too many retries when configuring device;"
1215 " giving up");
1216 pvr2_hdw_render_useless(hdw);
1217 break;
1218 }
1219 if (tryCount > 1) {
1220 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1221 "Retrying device reconfiguration");
1222 }
1223 pvr2_trace(PVR2_TRACE_INIT,
1224 "subsys mask changing 0x%lx:0x%lx"
1225 " from 0x%lx to 0x%lx",
1226 msk,val,hdw->subsys_enabled_mask,nmsk);
1227
1228 vmsk = (nmsk ^ hdw->subsys_enabled_mask) &
1229 hdw->subsys_enabled_mask;
1230 if (vmsk) {
1231 if (vmsk & (1<<PVR2_SUBSYS_B_ENC_RUN)) {
1232 pvr2_trace(PVR2_TRACE_CTL,
1233 "/*---TRACE_CTL----*/"
1234 " pvr2_encoder_stop");
1235 ret = pvr2_encoder_stop(hdw);
1236 if (ret) {
1237 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1238 "Error recovery initiated");
1239 hdw->subsys_enabled_mask &=
1240 ~FIRMWARE_RECOVERY_BITS;
1241 continue;
1242 }
1243 }
1244 if (vmsk & (1<<PVR2_SUBSYS_B_USBSTREAM_RUN)) {
1245 pvr2_trace(PVR2_TRACE_CTL,
1246 "/*---TRACE_CTL----*/"
1247 " pvr2_hdw_cmd_usbstream(0)");
1248 pvr2_hdw_cmd_usbstream(hdw,0);
1249 }
1250 if (vmsk & (1<<PVR2_SUBSYS_B_DIGITIZER_RUN)) {
1251 pvr2_trace(PVR2_TRACE_CTL,
1252 "/*---TRACE_CTL----*/"
1253 " decoder disable");
1254 if (hdw->decoder_ctrl) {
1255 hdw->decoder_ctrl->enable(
1256 hdw->decoder_ctrl->ctxt,0);
1257 } else {
1258 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1259 "WARNING:"
1260 " No decoder present");
1261 }
1262 hdw->subsys_enabled_mask &=
1263 ~(1<<PVR2_SUBSYS_B_DIGITIZER_RUN);
1264 }
1265 if (vmsk & PVR2_SUBSYS_CFG_ALL) {
1266 hdw->subsys_enabled_mask &=
1267 ~(vmsk & PVR2_SUBSYS_CFG_ALL);
1268 }
1269 }
1270 vmsk = (nmsk ^ hdw->subsys_enabled_mask) & nmsk;
1271 if (vmsk) {
1272 if (vmsk & (1<<PVR2_SUBSYS_B_ENC_FIRMWARE)) {
1273 pvr2_trace(PVR2_TRACE_CTL,
1274 "/*---TRACE_CTL----*/"
1275 " pvr2_upload_firmware2");
1276 ret = pvr2_upload_firmware2(hdw);
1277 if (ret) {
1278 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1279 "Failure uploading encoder"
1280 " firmware");
1281 pvr2_hdw_render_useless(hdw);
1282 break;
1283 }
1284 }
1285 if (vmsk & (1<<PVR2_SUBSYS_B_ENC_CFG)) {
1286 pvr2_trace(PVR2_TRACE_CTL,
1287 "/*---TRACE_CTL----*/"
1288 " pvr2_encoder_configure");
1289 ret = pvr2_encoder_configure(hdw);
1290 if (ret) {
1291 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1292 "Error recovery initiated");
1293 hdw->subsys_enabled_mask &=
1294 ~FIRMWARE_RECOVERY_BITS;
1295 continue;
1296 }
1297 }
1298 if (vmsk & (1<<PVR2_SUBSYS_B_DIGITIZER_RUN)) {
1299 pvr2_trace(PVR2_TRACE_CTL,
1300 "/*---TRACE_CTL----*/"
1301 " decoder enable");
1302 if (hdw->decoder_ctrl) {
1303 hdw->decoder_ctrl->enable(
1304 hdw->decoder_ctrl->ctxt,!0);
1305 } else {
1306 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1307 "WARNING:"
1308 " No decoder present");
1309 }
1310 hdw->subsys_enabled_mask |=
1311 (1<<PVR2_SUBSYS_B_DIGITIZER_RUN);
1312 }
1313 if (vmsk & (1<<PVR2_SUBSYS_B_USBSTREAM_RUN)) {
1314 pvr2_trace(PVR2_TRACE_CTL,
1315 "/*---TRACE_CTL----*/"
1316 " pvr2_hdw_cmd_usbstream(1)");
1317 pvr2_hdw_cmd_usbstream(hdw,!0);
1318 }
1319 if (vmsk & (1<<PVR2_SUBSYS_B_ENC_RUN)) {
1320 pvr2_trace(PVR2_TRACE_CTL,
1321 "/*---TRACE_CTL----*/"
1322 " pvr2_encoder_start");
1323 ret = pvr2_encoder_start(hdw);
1324 if (ret) {
1325 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1326 "Error recovery initiated");
1327 hdw->subsys_enabled_mask &=
1328 ~FIRMWARE_RECOVERY_BITS;
1329 continue;
1330 }
1331 }
1332 }
1333 }
1334}
1335
1336
1337void pvr2_hdw_subsys_bit_chg(struct pvr2_hdw *hdw,
1338 unsigned long msk,unsigned long val)
1339{
1340 LOCK_TAKE(hdw->big_lock); do {
1341 pvr2_hdw_subsys_bit_chg_no_lock(hdw,msk,val);
1342 } while (0); LOCK_GIVE(hdw->big_lock);
1343}
1344
1345
Mike Iselyd8554972006-06-26 20:58:46 -03001346unsigned long pvr2_hdw_subsys_get(struct pvr2_hdw *hdw)
1347{
1348 return hdw->subsys_enabled_mask;
1349}
1350
1351
1352unsigned long pvr2_hdw_subsys_stream_get(struct pvr2_hdw *hdw)
1353{
1354 return hdw->subsys_stream_mask;
1355}
1356
1357
Adrian Bunk07e337e2006-06-30 11:30:20 -03001358static void pvr2_hdw_subsys_stream_bit_chg_no_lock(struct pvr2_hdw *hdw,
1359 unsigned long msk,
1360 unsigned long val)
Mike Iselyd8554972006-06-26 20:58:46 -03001361{
1362 unsigned long val2;
1363 msk &= PVR2_SUBSYS_ALL;
1364 val2 = ((hdw->subsys_stream_mask & ~msk) | (val & msk));
1365 pvr2_trace(PVR2_TRACE_INIT,
1366 "stream mask changing 0x%lx:0x%lx from 0x%lx to 0x%lx",
1367 msk,val,hdw->subsys_stream_mask,val2);
1368 hdw->subsys_stream_mask = val2;
1369}
1370
1371
1372void pvr2_hdw_subsys_stream_bit_chg(struct pvr2_hdw *hdw,
1373 unsigned long msk,
1374 unsigned long val)
1375{
1376 LOCK_TAKE(hdw->big_lock); do {
1377 pvr2_hdw_subsys_stream_bit_chg_no_lock(hdw,msk,val);
1378 } while (0); LOCK_GIVE(hdw->big_lock);
1379}
1380
1381
Adrian Bunk07e337e2006-06-30 11:30:20 -03001382static int pvr2_hdw_set_streaming_no_lock(struct pvr2_hdw *hdw,int enableFl)
Mike Iselyd8554972006-06-26 20:58:46 -03001383{
1384 if ((!enableFl) == !(hdw->flag_streaming_enabled)) return 0;
1385 if (enableFl) {
1386 pvr2_trace(PVR2_TRACE_START_STOP,
1387 "/*--TRACE_STREAM--*/ enable");
1388 pvr2_hdw_subsys_bit_chg_no_lock(hdw,~0,~0);
1389 } else {
1390 pvr2_trace(PVR2_TRACE_START_STOP,
1391 "/*--TRACE_STREAM--*/ disable");
1392 pvr2_hdw_subsys_bit_chg_no_lock(hdw,hdw->subsys_stream_mask,0);
1393 }
1394 if (!hdw->flag_ok) return -EIO;
1395 hdw->flag_streaming_enabled = enableFl != 0;
1396 return 0;
1397}
1398
1399
1400int pvr2_hdw_get_streaming(struct pvr2_hdw *hdw)
1401{
1402 return hdw->flag_streaming_enabled != 0;
1403}
1404
1405
1406int pvr2_hdw_set_streaming(struct pvr2_hdw *hdw,int enable_flag)
1407{
1408 int ret;
1409 LOCK_TAKE(hdw->big_lock); do {
1410 ret = pvr2_hdw_set_streaming_no_lock(hdw,enable_flag);
1411 } while (0); LOCK_GIVE(hdw->big_lock);
1412 return ret;
1413}
1414
1415
Adrian Bunk07e337e2006-06-30 11:30:20 -03001416static int pvr2_hdw_set_stream_type_no_lock(struct pvr2_hdw *hdw,
1417 enum pvr2_config config)
Mike Iselyd8554972006-06-26 20:58:46 -03001418{
1419 unsigned long sm = hdw->subsys_enabled_mask;
1420 if (!hdw->flag_ok) return -EIO;
1421 pvr2_hdw_subsys_bit_chg_no_lock(hdw,hdw->subsys_stream_mask,0);
1422 hdw->config = config;
1423 pvr2_hdw_subsys_bit_chg_no_lock(hdw,~0,sm);
1424 return 0;
1425}
1426
1427
1428int pvr2_hdw_set_stream_type(struct pvr2_hdw *hdw,enum pvr2_config config)
1429{
1430 int ret;
1431 if (!hdw->flag_ok) return -EIO;
1432 LOCK_TAKE(hdw->big_lock);
1433 ret = pvr2_hdw_set_stream_type_no_lock(hdw,config);
1434 LOCK_GIVE(hdw->big_lock);
1435 return ret;
1436}
1437
1438
1439static int get_default_tuner_type(struct pvr2_hdw *hdw)
1440{
1441 int unit_number = hdw->unit_number;
1442 int tp = -1;
1443 if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
1444 tp = tuner[unit_number];
1445 }
1446 if (tp < 0) return -EINVAL;
1447 hdw->tuner_type = tp;
1448 return 0;
1449}
1450
1451
1452static v4l2_std_id get_default_standard(struct pvr2_hdw *hdw)
1453{
1454 int unit_number = hdw->unit_number;
1455 int tp = 0;
1456 if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
1457 tp = video_std[unit_number];
1458 }
1459 return tp;
1460}
1461
1462
1463static unsigned int get_default_error_tolerance(struct pvr2_hdw *hdw)
1464{
1465 int unit_number = hdw->unit_number;
1466 int tp = 0;
1467 if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
1468 tp = tolerance[unit_number];
1469 }
1470 return tp;
1471}
1472
1473
1474static int pvr2_hdw_check_firmware(struct pvr2_hdw *hdw)
1475{
1476 /* Try a harmless request to fetch the eeprom's address over
1477 endpoint 1. See what happens. Only the full FX2 image can
1478 respond to this. If this probe fails then likely the FX2
1479 firmware needs be loaded. */
1480 int result;
1481 LOCK_TAKE(hdw->ctl_lock); do {
1482 hdw->cmd_buffer[0] = 0xeb;
1483 result = pvr2_send_request_ex(hdw,HZ*1,!0,
1484 hdw->cmd_buffer,1,
1485 hdw->cmd_buffer,1);
1486 if (result < 0) break;
1487 } while(0); LOCK_GIVE(hdw->ctl_lock);
1488 if (result) {
1489 pvr2_trace(PVR2_TRACE_INIT,
1490 "Probe of device endpoint 1 result status %d",
1491 result);
1492 } else {
1493 pvr2_trace(PVR2_TRACE_INIT,
1494 "Probe of device endpoint 1 succeeded");
1495 }
1496 return result == 0;
1497}
1498
1499static void pvr2_hdw_setup_std(struct pvr2_hdw *hdw)
1500{
1501 char buf[40];
1502 unsigned int bcnt;
1503 v4l2_std_id std1,std2;
1504
1505 std1 = get_default_standard(hdw);
1506
1507 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),hdw->std_mask_eeprom);
1508 pvr2_trace(PVR2_TRACE_INIT,
1509 "Supported video standard(s) reported by eeprom: %.*s",
1510 bcnt,buf);
1511
1512 hdw->std_mask_avail = hdw->std_mask_eeprom;
1513
1514 std2 = std1 & ~hdw->std_mask_avail;
1515 if (std2) {
1516 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),std2);
1517 pvr2_trace(PVR2_TRACE_INIT,
1518 "Expanding supported video standards"
1519 " to include: %.*s",
1520 bcnt,buf);
1521 hdw->std_mask_avail |= std2;
1522 }
1523
1524 pvr2_hdw_internal_set_std_avail(hdw);
1525
1526 if (std1) {
1527 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),std1);
1528 pvr2_trace(PVR2_TRACE_INIT,
1529 "Initial video standard forced to %.*s",
1530 bcnt,buf);
1531 hdw->std_mask_cur = std1;
1532 hdw->std_dirty = !0;
1533 pvr2_hdw_internal_find_stdenum(hdw);
1534 return;
1535 }
1536
1537 if (hdw->std_enum_cnt > 1) {
1538 // Autoselect the first listed standard
1539 hdw->std_enum_cur = 1;
1540 hdw->std_mask_cur = hdw->std_defs[hdw->std_enum_cur-1].id;
1541 hdw->std_dirty = !0;
1542 pvr2_trace(PVR2_TRACE_INIT,
1543 "Initial video standard auto-selected to %s",
1544 hdw->std_defs[hdw->std_enum_cur-1].name);
1545 return;
1546 }
1547
Mike Isely0885ba12006-06-25 21:30:47 -03001548 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
Mike Iselyd8554972006-06-26 20:58:46 -03001549 "Unable to select a viable initial video standard");
1550}
1551
1552
1553static void pvr2_hdw_setup_low(struct pvr2_hdw *hdw)
1554{
1555 int ret;
1556 unsigned int idx;
1557 struct pvr2_ctrl *cptr;
1558 int reloadFl = 0;
1559 if (!reloadFl) {
1560 reloadFl = (hdw->usb_intf->cur_altsetting->desc.bNumEndpoints
1561 == 0);
1562 if (reloadFl) {
1563 pvr2_trace(PVR2_TRACE_INIT,
1564 "USB endpoint config looks strange"
1565 "; possibly firmware needs to be loaded");
1566 }
1567 }
1568 if (!reloadFl) {
1569 reloadFl = !pvr2_hdw_check_firmware(hdw);
1570 if (reloadFl) {
1571 pvr2_trace(PVR2_TRACE_INIT,
1572 "Check for FX2 firmware failed"
1573 "; possibly firmware needs to be loaded");
1574 }
1575 }
1576 if (reloadFl) {
1577 if (pvr2_upload_firmware1(hdw) != 0) {
1578 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1579 "Failure uploading firmware1");
1580 }
1581 return;
1582 }
1583 hdw->fw1_state = FW1_STATE_OK;
1584
1585 if (initusbreset) {
1586 pvr2_hdw_device_reset(hdw);
1587 }
1588 if (!pvr2_hdw_dev_ok(hdw)) return;
1589
1590 for (idx = 0; idx < pvr2_client_lists[hdw->hdw_type].cnt; idx++) {
1591 request_module(pvr2_client_lists[hdw->hdw_type].lst[idx]);
1592 }
1593
1594 pvr2_hdw_cmd_powerup(hdw);
1595 if (!pvr2_hdw_dev_ok(hdw)) return;
1596
1597 if (pvr2_upload_firmware2(hdw)){
1598 pvr2_trace(PVR2_TRACE_ERROR_LEGS,"device unstable!!");
1599 pvr2_hdw_render_useless(hdw);
1600 return;
1601 }
1602
1603 // This step MUST happen after the earlier powerup step.
1604 pvr2_i2c_core_init(hdw);
1605 if (!pvr2_hdw_dev_ok(hdw)) return;
1606
Mike Iselyc05c0462006-06-25 20:04:25 -03001607 for (idx = 0; idx < CTRLDEF_COUNT; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03001608 cptr = hdw->controls + idx;
1609 if (cptr->info->skip_init) continue;
1610 if (!cptr->info->set_value) continue;
1611 cptr->info->set_value(cptr,~0,cptr->info->default_value);
1612 }
1613
1614 // Do not use pvr2_reset_ctl_endpoints() here. It is not
1615 // thread-safe against the normal pvr2_send_request() mechanism.
1616 // (We should make it thread safe).
1617
1618 ret = pvr2_hdw_get_eeprom_addr(hdw);
1619 if (!pvr2_hdw_dev_ok(hdw)) return;
1620 if (ret < 0) {
1621 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1622 "Unable to determine location of eeprom, skipping");
1623 } else {
1624 hdw->eeprom_addr = ret;
1625 pvr2_eeprom_analyze(hdw);
1626 if (!pvr2_hdw_dev_ok(hdw)) return;
1627 }
1628
1629 pvr2_hdw_setup_std(hdw);
1630
1631 if (!get_default_tuner_type(hdw)) {
1632 pvr2_trace(PVR2_TRACE_INIT,
1633 "pvr2_hdw_setup: Tuner type overridden to %d",
1634 hdw->tuner_type);
1635 }
1636
1637 hdw->tuner_updated = !0;
1638 pvr2_i2c_core_check_stale(hdw);
1639 hdw->tuner_updated = 0;
1640
1641 if (!pvr2_hdw_dev_ok(hdw)) return;
1642
1643 pvr2_hdw_commit_ctl_internal(hdw);
1644 if (!pvr2_hdw_dev_ok(hdw)) return;
1645
1646 hdw->vid_stream = pvr2_stream_create();
1647 if (!pvr2_hdw_dev_ok(hdw)) return;
1648 pvr2_trace(PVR2_TRACE_INIT,
1649 "pvr2_hdw_setup: video stream is %p",hdw->vid_stream);
1650 if (hdw->vid_stream) {
1651 idx = get_default_error_tolerance(hdw);
1652 if (idx) {
1653 pvr2_trace(PVR2_TRACE_INIT,
1654 "pvr2_hdw_setup: video stream %p"
1655 " setting tolerance %u",
1656 hdw->vid_stream,idx);
1657 }
1658 pvr2_stream_setup(hdw->vid_stream,hdw->usb_dev,
1659 PVR2_VID_ENDPOINT,idx);
1660 }
1661
1662 if (!pvr2_hdw_dev_ok(hdw)) return;
1663
1664 /* Make sure everything is up to date */
1665 pvr2_i2c_core_sync(hdw);
1666
1667 if (!pvr2_hdw_dev_ok(hdw)) return;
1668
1669 hdw->flag_init_ok = !0;
1670}
1671
1672
1673int pvr2_hdw_setup(struct pvr2_hdw *hdw)
1674{
1675 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_setup(hdw=%p) begin",hdw);
1676 LOCK_TAKE(hdw->big_lock); do {
1677 pvr2_hdw_setup_low(hdw);
1678 pvr2_trace(PVR2_TRACE_INIT,
1679 "pvr2_hdw_setup(hdw=%p) done, ok=%d init_ok=%d",
1680 hdw,hdw->flag_ok,hdw->flag_init_ok);
1681 if (pvr2_hdw_dev_ok(hdw)) {
1682 if (pvr2_hdw_init_ok(hdw)) {
1683 pvr2_trace(
1684 PVR2_TRACE_INFO,
1685 "Device initialization"
1686 " completed successfully.");
1687 break;
1688 }
1689 if (hdw->fw1_state == FW1_STATE_RELOAD) {
1690 pvr2_trace(
1691 PVR2_TRACE_INFO,
1692 "Device microcontroller firmware"
1693 " (re)loaded; it should now reset"
1694 " and reconnect.");
1695 break;
1696 }
1697 pvr2_trace(
1698 PVR2_TRACE_ERROR_LEGS,
1699 "Device initialization was not successful.");
1700 if (hdw->fw1_state == FW1_STATE_MISSING) {
1701 pvr2_trace(
1702 PVR2_TRACE_ERROR_LEGS,
1703 "Giving up since device"
1704 " microcontroller firmware"
1705 " appears to be missing.");
1706 break;
1707 }
1708 }
1709 if (procreload) {
1710 pvr2_trace(
1711 PVR2_TRACE_ERROR_LEGS,
1712 "Attempting pvrusb2 recovery by reloading"
1713 " primary firmware.");
1714 pvr2_trace(
1715 PVR2_TRACE_ERROR_LEGS,
1716 "If this works, device should disconnect"
1717 " and reconnect in a sane state.");
1718 hdw->fw1_state = FW1_STATE_UNKNOWN;
1719 pvr2_upload_firmware1(hdw);
1720 } else {
1721 pvr2_trace(
1722 PVR2_TRACE_ERROR_LEGS,
1723 "***WARNING*** pvrusb2 device hardware"
1724 " appears to be jammed"
1725 " and I can't clear it.");
1726 pvr2_trace(
1727 PVR2_TRACE_ERROR_LEGS,
1728 "You might need to power cycle"
1729 " the pvrusb2 device"
1730 " in order to recover.");
1731 }
1732 } while (0); LOCK_GIVE(hdw->big_lock);
1733 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_setup(hdw=%p) end",hdw);
1734 return hdw->flag_init_ok;
1735}
1736
1737
1738/* Create and return a structure for interacting with the underlying
1739 hardware */
1740struct pvr2_hdw *pvr2_hdw_create(struct usb_interface *intf,
1741 const struct usb_device_id *devid)
1742{
1743 unsigned int idx,cnt1,cnt2;
1744 struct pvr2_hdw *hdw;
1745 unsigned int hdw_type;
1746 int valid_std_mask;
1747 struct pvr2_ctrl *cptr;
1748 __u8 ifnum;
Mike Iselyb30d2442006-06-25 20:05:01 -03001749 struct v4l2_queryctrl qctrl;
1750 struct pvr2_ctl_info *ciptr;
Mike Iselyd8554972006-06-26 20:58:46 -03001751
1752 hdw_type = devid - pvr2_device_table;
1753 if (hdw_type >=
1754 sizeof(pvr2_device_names)/sizeof(pvr2_device_names[0])) {
1755 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1756 "Bogus device type of %u reported",hdw_type);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001757 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001758 }
1759
1760 hdw = kmalloc(sizeof(*hdw),GFP_KERNEL);
1761 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_create: hdw=%p, type \"%s\"",
1762 hdw,pvr2_device_names[hdw_type]);
1763 if (!hdw) goto fail;
1764 memset(hdw,0,sizeof(*hdw));
Mike Iselyb30d2442006-06-25 20:05:01 -03001765 cx2341x_fill_defaults(&hdw->enc_ctl_state);
Mike Iselyd8554972006-06-26 20:58:46 -03001766
Mike Iselyc05c0462006-06-25 20:04:25 -03001767 hdw->control_cnt = CTRLDEF_COUNT;
Mike Iselyb30d2442006-06-25 20:05:01 -03001768 hdw->control_cnt += MPEGDEF_COUNT;
Mike Iselyc05c0462006-06-25 20:04:25 -03001769 hdw->controls = kmalloc(sizeof(struct pvr2_ctrl) * hdw->control_cnt,
Mike Iselyd8554972006-06-26 20:58:46 -03001770 GFP_KERNEL);
1771 if (!hdw->controls) goto fail;
Mike Iselyc05c0462006-06-25 20:04:25 -03001772 memset(hdw->controls,0,sizeof(struct pvr2_ctrl) * hdw->control_cnt);
Mike Iselyd8554972006-06-26 20:58:46 -03001773 hdw->hdw_type = hdw_type;
Mike Iselyc05c0462006-06-25 20:04:25 -03001774 for (idx = 0; idx < hdw->control_cnt; idx++) {
1775 cptr = hdw->controls + idx;
1776 cptr->hdw = hdw;
1777 }
Mike Iselyd8554972006-06-26 20:58:46 -03001778 for (idx = 0; idx < 32; idx++) {
1779 hdw->std_mask_ptrs[idx] = hdw->std_mask_names[idx];
1780 }
Mike Iselyc05c0462006-06-25 20:04:25 -03001781 for (idx = 0; idx < CTRLDEF_COUNT; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03001782 cptr = hdw->controls + idx;
Mike Iselyd8554972006-06-26 20:58:46 -03001783 cptr->info = control_defs+idx;
1784 }
Mike Iselyb30d2442006-06-25 20:05:01 -03001785 /* Define and configure additional controls from cx2341x module. */
1786 hdw->mpeg_ctrl_info = kmalloc(
1787 sizeof(*(hdw->mpeg_ctrl_info)) * MPEGDEF_COUNT, GFP_KERNEL);
1788 if (!hdw->mpeg_ctrl_info) goto fail;
1789 memset(hdw->mpeg_ctrl_info,0,
1790 sizeof(*(hdw->mpeg_ctrl_info)) * MPEGDEF_COUNT);
1791 for (idx = 0; idx < MPEGDEF_COUNT; idx++) {
1792 cptr = hdw->controls + idx + CTRLDEF_COUNT;
1793 ciptr = &(hdw->mpeg_ctrl_info[idx].info);
1794 ciptr->desc = hdw->mpeg_ctrl_info[idx].desc;
1795 ciptr->name = mpeg_ids[idx].strid;
1796 ciptr->v4l_id = mpeg_ids[idx].id;
1797 ciptr->skip_init = !0;
1798 ciptr->get_value = ctrl_cx2341x_get;
1799 ciptr->get_v4lflags = ctrl_cx2341x_getv4lflags;
1800 ciptr->is_dirty = ctrl_cx2341x_is_dirty;
1801 if (!idx) ciptr->clear_dirty = ctrl_cx2341x_clear_dirty;
1802 qctrl.id = ciptr->v4l_id;
1803 cx2341x_ctrl_query(&hdw->enc_ctl_state,&qctrl);
1804 if (!(qctrl.flags & V4L2_CTRL_FLAG_READ_ONLY)) {
1805 ciptr->set_value = ctrl_cx2341x_set;
1806 }
1807 strncpy(hdw->mpeg_ctrl_info[idx].desc,qctrl.name,
1808 PVR2_CTLD_INFO_DESC_SIZE);
1809 hdw->mpeg_ctrl_info[idx].desc[PVR2_CTLD_INFO_DESC_SIZE-1] = 0;
1810 ciptr->default_value = qctrl.default_value;
1811 switch (qctrl.type) {
1812 default:
1813 case V4L2_CTRL_TYPE_INTEGER:
1814 ciptr->type = pvr2_ctl_int;
1815 ciptr->def.type_int.min_value = qctrl.minimum;
1816 ciptr->def.type_int.max_value = qctrl.maximum;
1817 break;
1818 case V4L2_CTRL_TYPE_BOOLEAN:
1819 ciptr->type = pvr2_ctl_bool;
1820 break;
1821 case V4L2_CTRL_TYPE_MENU:
1822 ciptr->type = pvr2_ctl_enum;
1823 ciptr->def.type_enum.value_names =
1824 cx2341x_ctrl_get_menu(ciptr->v4l_id);
1825 for (cnt1 = 0;
1826 ciptr->def.type_enum.value_names[cnt1] != NULL;
1827 cnt1++) { }
1828 ciptr->def.type_enum.count = cnt1;
1829 break;
1830 }
1831 cptr->info = ciptr;
1832 }
Mike Iselyd8554972006-06-26 20:58:46 -03001833
1834 // Initialize video standard enum dynamic control
1835 cptr = pvr2_hdw_get_ctrl_by_id(hdw,PVR2_CID_STDENUM);
1836 if (cptr) {
1837 memcpy(&hdw->std_info_enum,cptr->info,
1838 sizeof(hdw->std_info_enum));
1839 cptr->info = &hdw->std_info_enum;
1840
1841 }
1842 // Initialize control data regarding video standard masks
1843 valid_std_mask = pvr2_std_get_usable();
1844 for (idx = 0; idx < 32; idx++) {
1845 if (!(valid_std_mask & (1 << idx))) continue;
1846 cnt1 = pvr2_std_id_to_str(
1847 hdw->std_mask_names[idx],
1848 sizeof(hdw->std_mask_names[idx])-1,
1849 1 << idx);
1850 hdw->std_mask_names[idx][cnt1] = 0;
1851 }
1852 cptr = pvr2_hdw_get_ctrl_by_id(hdw,PVR2_CID_STDAVAIL);
1853 if (cptr) {
1854 memcpy(&hdw->std_info_avail,cptr->info,
1855 sizeof(hdw->std_info_avail));
1856 cptr->info = &hdw->std_info_avail;
1857 hdw->std_info_avail.def.type_bitmask.bit_names =
1858 hdw->std_mask_ptrs;
1859 hdw->std_info_avail.def.type_bitmask.valid_bits =
1860 valid_std_mask;
1861 }
1862 cptr = pvr2_hdw_get_ctrl_by_id(hdw,PVR2_CID_STDCUR);
1863 if (cptr) {
1864 memcpy(&hdw->std_info_cur,cptr->info,
1865 sizeof(hdw->std_info_cur));
1866 cptr->info = &hdw->std_info_cur;
1867 hdw->std_info_cur.def.type_bitmask.bit_names =
1868 hdw->std_mask_ptrs;
1869 hdw->std_info_avail.def.type_bitmask.valid_bits =
1870 valid_std_mask;
1871 }
1872
1873 hdw->eeprom_addr = -1;
1874 hdw->unit_number = -1;
1875 hdw->v4l_minor_number = -1;
1876 hdw->ctl_write_buffer = kmalloc(PVR2_CTL_BUFFSIZE,GFP_KERNEL);
1877 if (!hdw->ctl_write_buffer) goto fail;
1878 hdw->ctl_read_buffer = kmalloc(PVR2_CTL_BUFFSIZE,GFP_KERNEL);
1879 if (!hdw->ctl_read_buffer) goto fail;
1880 hdw->ctl_write_urb = usb_alloc_urb(0,GFP_KERNEL);
1881 if (!hdw->ctl_write_urb) goto fail;
1882 hdw->ctl_read_urb = usb_alloc_urb(0,GFP_KERNEL);
1883 if (!hdw->ctl_read_urb) goto fail;
1884
1885 down(&pvr2_unit_sem); do {
1886 for (idx = 0; idx < PVR_NUM; idx++) {
1887 if (unit_pointers[idx]) continue;
1888 hdw->unit_number = idx;
1889 unit_pointers[idx] = hdw;
1890 break;
1891 }
1892 } while (0); up(&pvr2_unit_sem);
1893
1894 cnt1 = 0;
1895 cnt2 = scnprintf(hdw->name+cnt1,sizeof(hdw->name)-cnt1,"pvrusb2");
1896 cnt1 += cnt2;
1897 if (hdw->unit_number >= 0) {
1898 cnt2 = scnprintf(hdw->name+cnt1,sizeof(hdw->name)-cnt1,"_%c",
1899 ('a' + hdw->unit_number));
1900 cnt1 += cnt2;
1901 }
1902 if (cnt1 >= sizeof(hdw->name)) cnt1 = sizeof(hdw->name)-1;
1903 hdw->name[cnt1] = 0;
1904
1905 pvr2_trace(PVR2_TRACE_INIT,"Driver unit number is %d, name is %s",
1906 hdw->unit_number,hdw->name);
1907
1908 hdw->tuner_type = -1;
1909 hdw->flag_ok = !0;
1910 /* Initialize the mask of subsystems that we will shut down when we
1911 stop streaming. */
1912 hdw->subsys_stream_mask = PVR2_SUBSYS_RUN_ALL;
1913 hdw->subsys_stream_mask |= (1<<PVR2_SUBSYS_B_ENC_CFG);
1914
1915 pvr2_trace(PVR2_TRACE_INIT,"subsys_stream_mask: 0x%lx",
1916 hdw->subsys_stream_mask);
1917
1918 hdw->usb_intf = intf;
1919 hdw->usb_dev = interface_to_usbdev(intf);
1920
1921 ifnum = hdw->usb_intf->cur_altsetting->desc.bInterfaceNumber;
1922 usb_set_interface(hdw->usb_dev,ifnum,0);
1923
1924 mutex_init(&hdw->ctl_lock_mutex);
1925 mutex_init(&hdw->big_lock_mutex);
1926
1927 return hdw;
1928 fail:
1929 if (hdw) {
Mariusz Kozlowski5e55d2c2006-11-08 15:34:31 +01001930 usb_free_urb(hdw->ctl_read_urb);
1931 usb_free_urb(hdw->ctl_write_urb);
Mike Iselyd8554972006-06-26 20:58:46 -03001932 if (hdw->ctl_read_buffer) kfree(hdw->ctl_read_buffer);
1933 if (hdw->ctl_write_buffer) kfree(hdw->ctl_write_buffer);
1934 if (hdw->controls) kfree(hdw->controls);
Mike Iselyb30d2442006-06-25 20:05:01 -03001935 if (hdw->mpeg_ctrl_info) kfree(hdw->mpeg_ctrl_info);
Mike Iselyd8554972006-06-26 20:58:46 -03001936 kfree(hdw);
1937 }
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001938 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001939}
1940
1941
1942/* Remove _all_ associations between this driver and the underlying USB
1943 layer. */
Adrian Bunk07e337e2006-06-30 11:30:20 -03001944static void pvr2_hdw_remove_usb_stuff(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03001945{
1946 if (hdw->flag_disconnected) return;
1947 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_remove_usb_stuff: hdw=%p",hdw);
1948 if (hdw->ctl_read_urb) {
1949 usb_kill_urb(hdw->ctl_read_urb);
1950 usb_free_urb(hdw->ctl_read_urb);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001951 hdw->ctl_read_urb = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001952 }
1953 if (hdw->ctl_write_urb) {
1954 usb_kill_urb(hdw->ctl_write_urb);
1955 usb_free_urb(hdw->ctl_write_urb);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001956 hdw->ctl_write_urb = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001957 }
1958 if (hdw->ctl_read_buffer) {
1959 kfree(hdw->ctl_read_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001960 hdw->ctl_read_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001961 }
1962 if (hdw->ctl_write_buffer) {
1963 kfree(hdw->ctl_write_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001964 hdw->ctl_write_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001965 }
1966 pvr2_hdw_render_useless_unlocked(hdw);
1967 hdw->flag_disconnected = !0;
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001968 hdw->usb_dev = NULL;
1969 hdw->usb_intf = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001970}
1971
1972
1973/* Destroy hardware interaction structure */
1974void pvr2_hdw_destroy(struct pvr2_hdw *hdw)
1975{
1976 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_destroy: hdw=%p",hdw);
1977 if (hdw->fw_buffer) {
1978 kfree(hdw->fw_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001979 hdw->fw_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001980 }
1981 if (hdw->vid_stream) {
1982 pvr2_stream_destroy(hdw->vid_stream);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001983 hdw->vid_stream = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001984 }
1985 if (hdw->audio_stat) {
1986 hdw->audio_stat->detach(hdw->audio_stat->ctxt);
1987 }
1988 if (hdw->decoder_ctrl) {
1989 hdw->decoder_ctrl->detach(hdw->decoder_ctrl->ctxt);
1990 }
1991 pvr2_i2c_core_done(hdw);
1992 pvr2_hdw_remove_usb_stuff(hdw);
1993 down(&pvr2_unit_sem); do {
1994 if ((hdw->unit_number >= 0) &&
1995 (hdw->unit_number < PVR_NUM) &&
1996 (unit_pointers[hdw->unit_number] == hdw)) {
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001997 unit_pointers[hdw->unit_number] = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001998 }
1999 } while (0); up(&pvr2_unit_sem);
Mike Iselyc05c0462006-06-25 20:04:25 -03002000 if (hdw->controls) kfree(hdw->controls);
Mike Iselyb30d2442006-06-25 20:05:01 -03002001 if (hdw->mpeg_ctrl_info) kfree(hdw->mpeg_ctrl_info);
Mike Iselyd8554972006-06-26 20:58:46 -03002002 if (hdw->std_defs) kfree(hdw->std_defs);
2003 if (hdw->std_enum_names) kfree(hdw->std_enum_names);
2004 kfree(hdw);
2005}
2006
2007
2008int pvr2_hdw_init_ok(struct pvr2_hdw *hdw)
2009{
2010 return hdw->flag_init_ok;
2011}
2012
2013
2014int pvr2_hdw_dev_ok(struct pvr2_hdw *hdw)
2015{
2016 return (hdw && hdw->flag_ok);
2017}
2018
2019
2020/* Called when hardware has been unplugged */
2021void pvr2_hdw_disconnect(struct pvr2_hdw *hdw)
2022{
2023 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_disconnect(hdw=%p)",hdw);
2024 LOCK_TAKE(hdw->big_lock);
2025 LOCK_TAKE(hdw->ctl_lock);
2026 pvr2_hdw_remove_usb_stuff(hdw);
2027 LOCK_GIVE(hdw->ctl_lock);
2028 LOCK_GIVE(hdw->big_lock);
2029}
2030
2031
2032// Attempt to autoselect an appropriate value for std_enum_cur given
2033// whatever is currently in std_mask_cur
Adrian Bunk07e337e2006-06-30 11:30:20 -03002034static void pvr2_hdw_internal_find_stdenum(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002035{
2036 unsigned int idx;
2037 for (idx = 1; idx < hdw->std_enum_cnt; idx++) {
2038 if (hdw->std_defs[idx-1].id == hdw->std_mask_cur) {
2039 hdw->std_enum_cur = idx;
2040 return;
2041 }
2042 }
2043 hdw->std_enum_cur = 0;
2044}
2045
2046
2047// Calculate correct set of enumerated standards based on currently known
2048// set of available standards bits.
Adrian Bunk07e337e2006-06-30 11:30:20 -03002049static void pvr2_hdw_internal_set_std_avail(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002050{
2051 struct v4l2_standard *newstd;
2052 unsigned int std_cnt;
2053 unsigned int idx;
2054
2055 newstd = pvr2_std_create_enum(&std_cnt,hdw->std_mask_avail);
2056
2057 if (hdw->std_defs) {
2058 kfree(hdw->std_defs);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002059 hdw->std_defs = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002060 }
2061 hdw->std_enum_cnt = 0;
2062 if (hdw->std_enum_names) {
2063 kfree(hdw->std_enum_names);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002064 hdw->std_enum_names = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002065 }
2066
2067 if (!std_cnt) {
2068 pvr2_trace(
2069 PVR2_TRACE_ERROR_LEGS,
2070 "WARNING: Failed to identify any viable standards");
2071 }
2072 hdw->std_enum_names = kmalloc(sizeof(char *)*(std_cnt+1),GFP_KERNEL);
2073 hdw->std_enum_names[0] = "none";
2074 for (idx = 0; idx < std_cnt; idx++) {
2075 hdw->std_enum_names[idx+1] =
2076 newstd[idx].name;
2077 }
2078 // Set up the dynamic control for this standard
2079 hdw->std_info_enum.def.type_enum.value_names = hdw->std_enum_names;
2080 hdw->std_info_enum.def.type_enum.count = std_cnt+1;
2081 hdw->std_defs = newstd;
2082 hdw->std_enum_cnt = std_cnt+1;
2083 hdw->std_enum_cur = 0;
2084 hdw->std_info_cur.def.type_bitmask.valid_bits = hdw->std_mask_avail;
2085}
2086
2087
2088int pvr2_hdw_get_stdenum_value(struct pvr2_hdw *hdw,
2089 struct v4l2_standard *std,
2090 unsigned int idx)
2091{
2092 int ret = -EINVAL;
2093 if (!idx) return ret;
2094 LOCK_TAKE(hdw->big_lock); do {
2095 if (idx >= hdw->std_enum_cnt) break;
2096 idx--;
2097 memcpy(std,hdw->std_defs+idx,sizeof(*std));
2098 ret = 0;
2099 } while (0); LOCK_GIVE(hdw->big_lock);
2100 return ret;
2101}
2102
2103
2104/* Get the number of defined controls */
2105unsigned int pvr2_hdw_get_ctrl_count(struct pvr2_hdw *hdw)
2106{
Mike Iselyc05c0462006-06-25 20:04:25 -03002107 return hdw->control_cnt;
Mike Iselyd8554972006-06-26 20:58:46 -03002108}
2109
2110
2111/* Retrieve a control handle given its index (0..count-1) */
2112struct pvr2_ctrl *pvr2_hdw_get_ctrl_by_index(struct pvr2_hdw *hdw,
2113 unsigned int idx)
2114{
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002115 if (idx >= hdw->control_cnt) return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002116 return hdw->controls + idx;
2117}
2118
2119
2120/* Retrieve a control handle given its index (0..count-1) */
2121struct pvr2_ctrl *pvr2_hdw_get_ctrl_by_id(struct pvr2_hdw *hdw,
2122 unsigned int ctl_id)
2123{
2124 struct pvr2_ctrl *cptr;
2125 unsigned int idx;
2126 int i;
2127
2128 /* This could be made a lot more efficient, but for now... */
Mike Iselyc05c0462006-06-25 20:04:25 -03002129 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002130 cptr = hdw->controls + idx;
2131 i = cptr->info->internal_id;
2132 if (i && (i == ctl_id)) return cptr;
2133 }
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002134 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002135}
2136
2137
Mike Iselya761f432006-06-25 20:04:44 -03002138/* Given a V4L ID, retrieve the control structure associated with it. */
Mike Iselyd8554972006-06-26 20:58:46 -03002139struct pvr2_ctrl *pvr2_hdw_get_ctrl_v4l(struct pvr2_hdw *hdw,unsigned int ctl_id)
2140{
2141 struct pvr2_ctrl *cptr;
2142 unsigned int idx;
2143 int i;
2144
2145 /* This could be made a lot more efficient, but for now... */
Mike Iselyc05c0462006-06-25 20:04:25 -03002146 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002147 cptr = hdw->controls + idx;
2148 i = cptr->info->v4l_id;
2149 if (i && (i == ctl_id)) return cptr;
2150 }
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002151 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002152}
2153
2154
Mike Iselya761f432006-06-25 20:04:44 -03002155/* Given a V4L ID for its immediate predecessor, retrieve the control
2156 structure associated with it. */
2157struct pvr2_ctrl *pvr2_hdw_get_ctrl_nextv4l(struct pvr2_hdw *hdw,
2158 unsigned int ctl_id)
2159{
2160 struct pvr2_ctrl *cptr,*cp2;
2161 unsigned int idx;
2162 int i;
2163
2164 /* This could be made a lot more efficient, but for now... */
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002165 cp2 = NULL;
Mike Iselya761f432006-06-25 20:04:44 -03002166 for (idx = 0; idx < hdw->control_cnt; idx++) {
2167 cptr = hdw->controls + idx;
2168 i = cptr->info->v4l_id;
2169 if (!i) continue;
2170 if (i <= ctl_id) continue;
2171 if (cp2 && (cp2->info->v4l_id < i)) continue;
2172 cp2 = cptr;
2173 }
2174 return cp2;
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002175 return NULL;
Mike Iselya761f432006-06-25 20:04:44 -03002176}
2177
2178
Mike Iselyd8554972006-06-26 20:58:46 -03002179static const char *get_ctrl_typename(enum pvr2_ctl_type tp)
2180{
2181 switch (tp) {
2182 case pvr2_ctl_int: return "integer";
2183 case pvr2_ctl_enum: return "enum";
Mike Isely33213962006-06-25 20:04:40 -03002184 case pvr2_ctl_bool: return "boolean";
Mike Iselyd8554972006-06-26 20:58:46 -03002185 case pvr2_ctl_bitmask: return "bitmask";
2186 }
2187 return "";
2188}
2189
2190
2191/* Commit all control changes made up to this point. Subsystems can be
2192 indirectly affected by these changes. For a given set of things being
2193 committed, we'll clear the affected subsystem bits and then once we're
2194 done committing everything we'll make a request to restore the subsystem
2195 state(s) back to their previous value before this function was called.
2196 Thus we can automatically reconfigure affected pieces of the driver as
2197 controls are changed. */
Adrian Bunk07e337e2006-06-30 11:30:20 -03002198static int pvr2_hdw_commit_ctl_internal(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002199{
2200 unsigned long saved_subsys_mask = hdw->subsys_enabled_mask;
2201 unsigned long stale_subsys_mask = 0;
2202 unsigned int idx;
2203 struct pvr2_ctrl *cptr;
2204 int value;
2205 int commit_flag = 0;
2206 char buf[100];
2207 unsigned int bcnt,ccnt;
2208
Mike Iselyc05c0462006-06-25 20:04:25 -03002209 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002210 cptr = hdw->controls + idx;
2211 if (cptr->info->is_dirty == 0) continue;
2212 if (!cptr->info->is_dirty(cptr)) continue;
2213 if (!commit_flag) {
2214 commit_flag = !0;
2215 }
2216
2217 bcnt = scnprintf(buf,sizeof(buf),"\"%s\" <-- ",
2218 cptr->info->name);
2219 value = 0;
2220 cptr->info->get_value(cptr,&value);
2221 pvr2_ctrl_value_to_sym_internal(cptr,~0,value,
2222 buf+bcnt,
2223 sizeof(buf)-bcnt,&ccnt);
2224 bcnt += ccnt;
2225 bcnt += scnprintf(buf+bcnt,sizeof(buf)-bcnt," <%s>",
2226 get_ctrl_typename(cptr->info->type));
2227 pvr2_trace(PVR2_TRACE_CTL,
2228 "/*--TRACE_COMMIT--*/ %.*s",
2229 bcnt,buf);
2230 }
2231
2232 if (!commit_flag) {
2233 /* Nothing has changed */
2234 return 0;
2235 }
2236
2237 /* When video standard changes, reset the hres and vres values -
2238 but if the user has pending changes there, then let the changes
2239 take priority. */
2240 if (hdw->std_dirty) {
2241 /* Rewrite the vertical resolution to be appropriate to the
2242 video standard that has been selected. */
2243 int nvres;
2244 if (hdw->std_mask_cur & V4L2_STD_525_60) {
2245 nvres = 480;
2246 } else {
2247 nvres = 576;
2248 }
2249 if (nvres != hdw->res_ver_val) {
2250 hdw->res_ver_val = nvres;
2251 hdw->res_ver_dirty = !0;
2252 }
Mike Iselyd8554972006-06-26 20:58:46 -03002253 }
2254
2255 if (hdw->std_dirty ||
Mike Isely434449f2006-08-08 09:10:06 -03002256 hdw->enc_stale ||
2257 hdw->srate_dirty ||
2258 hdw->res_ver_dirty ||
2259 hdw->res_hor_dirty ||
Mike Iselyb46cfa82006-06-25 20:04:53 -03002260 0) {
Mike Iselyd8554972006-06-26 20:58:46 -03002261 /* If any of this changes, then the encoder needs to be
2262 reconfigured, and we need to reset the stream. */
2263 stale_subsys_mask |= (1<<PVR2_SUBSYS_B_ENC_CFG);
Mike Iselyd8554972006-06-26 20:58:46 -03002264 }
2265
Mike Iselyb30d2442006-06-25 20:05:01 -03002266 if (hdw->srate_dirty) {
2267 /* Write new sample rate into control structure since
2268 * the master copy is stale. We must track srate
2269 * separate from the mpeg control structure because
2270 * other logic also uses this value. */
2271 struct v4l2_ext_controls cs;
2272 struct v4l2_ext_control c1;
2273 memset(&cs,0,sizeof(cs));
2274 memset(&c1,0,sizeof(c1));
2275 cs.controls = &c1;
2276 cs.count = 1;
2277 c1.id = V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ;
2278 c1.value = hdw->srate_val;
2279 cx2341x_ext_ctrls(&hdw->enc_ctl_state,&cs,VIDIOC_S_EXT_CTRLS);
2280 }
Mike Iselyc05c0462006-06-25 20:04:25 -03002281
Mike Iselyd8554972006-06-26 20:58:46 -03002282 /* Scan i2c core at this point - before we clear all the dirty
2283 bits. Various parts of the i2c core will notice dirty bits as
2284 appropriate and arrange to broadcast or directly send updates to
2285 the client drivers in order to keep everything in sync */
2286 pvr2_i2c_core_check_stale(hdw);
2287
Mike Iselyc05c0462006-06-25 20:04:25 -03002288 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002289 cptr = hdw->controls + idx;
2290 if (!cptr->info->clear_dirty) continue;
2291 cptr->info->clear_dirty(cptr);
2292 }
2293
2294 /* Now execute i2c core update */
2295 pvr2_i2c_core_sync(hdw);
2296
2297 pvr2_hdw_subsys_bit_chg_no_lock(hdw,stale_subsys_mask,0);
2298 pvr2_hdw_subsys_bit_chg_no_lock(hdw,~0,saved_subsys_mask);
2299
2300 return 0;
2301}
2302
2303
2304int pvr2_hdw_commit_ctl(struct pvr2_hdw *hdw)
2305{
2306 LOCK_TAKE(hdw->big_lock); do {
2307 pvr2_hdw_commit_ctl_internal(hdw);
2308 } while (0); LOCK_GIVE(hdw->big_lock);
2309 return 0;
2310}
2311
2312
2313void pvr2_hdw_poll(struct pvr2_hdw *hdw)
2314{
2315 LOCK_TAKE(hdw->big_lock); do {
2316 pvr2_i2c_core_sync(hdw);
2317 } while (0); LOCK_GIVE(hdw->big_lock);
2318}
2319
2320
2321void pvr2_hdw_setup_poll_trigger(struct pvr2_hdw *hdw,
2322 void (*func)(void *),
2323 void *data)
2324{
2325 LOCK_TAKE(hdw->big_lock); do {
2326 hdw->poll_trigger_func = func;
2327 hdw->poll_trigger_data = data;
2328 } while (0); LOCK_GIVE(hdw->big_lock);
2329}
2330
2331
2332void pvr2_hdw_poll_trigger_unlocked(struct pvr2_hdw *hdw)
2333{
2334 if (hdw->poll_trigger_func) {
2335 hdw->poll_trigger_func(hdw->poll_trigger_data);
2336 }
2337}
2338
Mike Iselyd8554972006-06-26 20:58:46 -03002339/* Return name for this driver instance */
2340const char *pvr2_hdw_get_driver_name(struct pvr2_hdw *hdw)
2341{
2342 return hdw->name;
2343}
2344
2345
2346/* Return bit mask indicating signal status */
Adrian Bunk07e337e2006-06-30 11:30:20 -03002347static unsigned int pvr2_hdw_get_signal_status_internal(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002348{
2349 unsigned int msk = 0;
2350 switch (hdw->input_val) {
2351 case PVR2_CVAL_INPUT_TV:
2352 case PVR2_CVAL_INPUT_RADIO:
2353 if (hdw->decoder_ctrl &&
2354 hdw->decoder_ctrl->tuned(hdw->decoder_ctrl->ctxt)) {
2355 msk |= PVR2_SIGNAL_OK;
2356 if (hdw->audio_stat &&
2357 hdw->audio_stat->status(hdw->audio_stat->ctxt)) {
2358 if (hdw->flag_stereo) {
2359 msk |= PVR2_SIGNAL_STEREO;
2360 }
2361 if (hdw->flag_bilingual) {
2362 msk |= PVR2_SIGNAL_SAP;
2363 }
2364 }
2365 }
2366 break;
2367 default:
2368 msk |= PVR2_SIGNAL_OK | PVR2_SIGNAL_STEREO;
2369 }
2370 return msk;
2371}
2372
2373
2374int pvr2_hdw_is_hsm(struct pvr2_hdw *hdw)
2375{
2376 int result;
2377 LOCK_TAKE(hdw->ctl_lock); do {
2378 hdw->cmd_buffer[0] = 0x0b;
2379 result = pvr2_send_request(hdw,
2380 hdw->cmd_buffer,1,
2381 hdw->cmd_buffer,1);
2382 if (result < 0) break;
2383 result = (hdw->cmd_buffer[0] != 0);
2384 } while(0); LOCK_GIVE(hdw->ctl_lock);
2385 return result;
2386}
2387
2388
2389/* Return bit mask indicating signal status */
2390unsigned int pvr2_hdw_get_signal_status(struct pvr2_hdw *hdw)
2391{
2392 unsigned int msk = 0;
2393 LOCK_TAKE(hdw->big_lock); do {
2394 msk = pvr2_hdw_get_signal_status_internal(hdw);
2395 } while (0); LOCK_GIVE(hdw->big_lock);
2396 return msk;
2397}
2398
2399
2400/* Get handle to video output stream */
2401struct pvr2_stream *pvr2_hdw_get_video_stream(struct pvr2_hdw *hp)
2402{
2403 return hp->vid_stream;
2404}
2405
2406
2407void pvr2_hdw_trigger_module_log(struct pvr2_hdw *hdw)
2408{
Mike Isely4f1a3e52006-06-25 20:04:31 -03002409 int nr = pvr2_hdw_get_unit_number(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03002410 LOCK_TAKE(hdw->big_lock); do {
2411 hdw->log_requested = !0;
Mike Isely4f1a3e52006-06-25 20:04:31 -03002412 printk(KERN_INFO "pvrusb2: ================= START STATUS CARD #%d =================\n", nr);
Mike Iselyd8554972006-06-26 20:58:46 -03002413 pvr2_i2c_core_check_stale(hdw);
2414 hdw->log_requested = 0;
2415 pvr2_i2c_core_sync(hdw);
Mike Iselyb30d2442006-06-25 20:05:01 -03002416 pvr2_trace(PVR2_TRACE_INFO,"cx2341x config:");
Hans Verkuil99eb44f2006-06-26 18:24:05 -03002417 cx2341x_log_status(&hdw->enc_ctl_state, "pvrusb2");
Mike Isely4f1a3e52006-06-25 20:04:31 -03002418 printk(KERN_INFO "pvrusb2: ================== END STATUS CARD #%d ==================\n", nr);
Mike Iselyd8554972006-06-26 20:58:46 -03002419 } while (0); LOCK_GIVE(hdw->big_lock);
2420}
2421
2422void pvr2_hdw_cpufw_set_enabled(struct pvr2_hdw *hdw, int enable_flag)
2423{
2424 int ret;
2425 u16 address;
2426 unsigned int pipe;
2427 LOCK_TAKE(hdw->big_lock); do {
2428 if ((hdw->fw_buffer == 0) == !enable_flag) break;
2429
2430 if (!enable_flag) {
2431 pvr2_trace(PVR2_TRACE_FIRMWARE,
2432 "Cleaning up after CPU firmware fetch");
2433 kfree(hdw->fw_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002434 hdw->fw_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002435 hdw->fw_size = 0;
2436 /* Now release the CPU. It will disconnect and
2437 reconnect later. */
2438 pvr2_hdw_cpureset_assert(hdw,0);
2439 break;
2440 }
2441
2442 pvr2_trace(PVR2_TRACE_FIRMWARE,
2443 "Preparing to suck out CPU firmware");
2444 hdw->fw_size = 0x2000;
2445 hdw->fw_buffer = kmalloc(hdw->fw_size,GFP_KERNEL);
2446 if (!hdw->fw_buffer) {
2447 hdw->fw_size = 0;
2448 break;
2449 }
2450
2451 memset(hdw->fw_buffer,0,hdw->fw_size);
2452
2453 /* We have to hold the CPU during firmware upload. */
2454 pvr2_hdw_cpureset_assert(hdw,1);
2455
2456 /* download the firmware from address 0000-1fff in 2048
2457 (=0x800) bytes chunk. */
2458
2459 pvr2_trace(PVR2_TRACE_FIRMWARE,"Grabbing CPU firmware");
2460 pipe = usb_rcvctrlpipe(hdw->usb_dev, 0);
2461 for(address = 0; address < hdw->fw_size; address += 0x800) {
2462 ret = usb_control_msg(hdw->usb_dev,pipe,0xa0,0xc0,
2463 address,0,
2464 hdw->fw_buffer+address,0x800,HZ);
2465 if (ret < 0) break;
2466 }
2467
2468 pvr2_trace(PVR2_TRACE_FIRMWARE,"Done grabbing CPU firmware");
2469
2470 } while (0); LOCK_GIVE(hdw->big_lock);
2471}
2472
2473
2474/* Return true if we're in a mode for retrieval CPU firmware */
2475int pvr2_hdw_cpufw_get_enabled(struct pvr2_hdw *hdw)
2476{
2477 return hdw->fw_buffer != 0;
2478}
2479
2480
2481int pvr2_hdw_cpufw_get(struct pvr2_hdw *hdw,unsigned int offs,
2482 char *buf,unsigned int cnt)
2483{
2484 int ret = -EINVAL;
2485 LOCK_TAKE(hdw->big_lock); do {
2486 if (!buf) break;
2487 if (!cnt) break;
2488
2489 if (!hdw->fw_buffer) {
2490 ret = -EIO;
2491 break;
2492 }
2493
2494 if (offs >= hdw->fw_size) {
2495 pvr2_trace(PVR2_TRACE_FIRMWARE,
2496 "Read firmware data offs=%d EOF",
2497 offs);
2498 ret = 0;
2499 break;
2500 }
2501
2502 if (offs + cnt > hdw->fw_size) cnt = hdw->fw_size - offs;
2503
2504 memcpy(buf,hdw->fw_buffer+offs,cnt);
2505
2506 pvr2_trace(PVR2_TRACE_FIRMWARE,
2507 "Read firmware data offs=%d cnt=%d",
2508 offs,cnt);
2509 ret = cnt;
2510 } while (0); LOCK_GIVE(hdw->big_lock);
2511
2512 return ret;
2513}
2514
2515
2516int pvr2_hdw_v4l_get_minor_number(struct pvr2_hdw *hdw)
2517{
2518 return hdw->v4l_minor_number;
2519}
2520
2521
2522/* Store the v4l minor device number */
2523void pvr2_hdw_v4l_store_minor_number(struct pvr2_hdw *hdw,int v)
2524{
2525 hdw->v4l_minor_number = v;
2526}
2527
2528
David Howells7d12e782006-10-05 14:55:46 +01002529static void pvr2_ctl_write_complete(struct urb *urb)
Mike Iselyd8554972006-06-26 20:58:46 -03002530{
2531 struct pvr2_hdw *hdw = urb->context;
2532 hdw->ctl_write_pend_flag = 0;
2533 if (hdw->ctl_read_pend_flag) return;
2534 complete(&hdw->ctl_done);
2535}
2536
2537
David Howells7d12e782006-10-05 14:55:46 +01002538static void pvr2_ctl_read_complete(struct urb *urb)
Mike Iselyd8554972006-06-26 20:58:46 -03002539{
2540 struct pvr2_hdw *hdw = urb->context;
2541 hdw->ctl_read_pend_flag = 0;
2542 if (hdw->ctl_write_pend_flag) return;
2543 complete(&hdw->ctl_done);
2544}
2545
2546
2547static void pvr2_ctl_timeout(unsigned long data)
2548{
2549 struct pvr2_hdw *hdw = (struct pvr2_hdw *)data;
2550 if (hdw->ctl_write_pend_flag || hdw->ctl_read_pend_flag) {
2551 hdw->ctl_timeout_flag = !0;
Mariusz Kozlowski5e55d2c2006-11-08 15:34:31 +01002552 if (hdw->ctl_write_pend_flag)
Mike Iselyd8554972006-06-26 20:58:46 -03002553 usb_unlink_urb(hdw->ctl_write_urb);
Mariusz Kozlowski5e55d2c2006-11-08 15:34:31 +01002554 if (hdw->ctl_read_pend_flag)
Mike Iselyd8554972006-06-26 20:58:46 -03002555 usb_unlink_urb(hdw->ctl_read_urb);
Mike Iselyd8554972006-06-26 20:58:46 -03002556 }
2557}
2558
2559
Mike Iselye61b6fc2006-07-18 22:42:18 -03002560/* Issue a command and get a response from the device. This extended
2561 version includes a probe flag (which if set means that device errors
2562 should not be logged or treated as fatal) and a timeout in jiffies.
2563 This can be used to non-lethally probe the health of endpoint 1. */
Adrian Bunk07e337e2006-06-30 11:30:20 -03002564static int pvr2_send_request_ex(struct pvr2_hdw *hdw,
2565 unsigned int timeout,int probe_fl,
2566 void *write_data,unsigned int write_len,
2567 void *read_data,unsigned int read_len)
Mike Iselyd8554972006-06-26 20:58:46 -03002568{
2569 unsigned int idx;
2570 int status = 0;
2571 struct timer_list timer;
2572 if (!hdw->ctl_lock_held) {
2573 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2574 "Attempted to execute control transfer"
2575 " without lock!!");
2576 return -EDEADLK;
2577 }
2578 if ((!hdw->flag_ok) && !probe_fl) {
2579 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2580 "Attempted to execute control transfer"
2581 " when device not ok");
2582 return -EIO;
2583 }
2584 if (!(hdw->ctl_read_urb && hdw->ctl_write_urb)) {
2585 if (!probe_fl) {
2586 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2587 "Attempted to execute control transfer"
2588 " when USB is disconnected");
2589 }
2590 return -ENOTTY;
2591 }
2592
2593 /* Ensure that we have sane parameters */
2594 if (!write_data) write_len = 0;
2595 if (!read_data) read_len = 0;
2596 if (write_len > PVR2_CTL_BUFFSIZE) {
2597 pvr2_trace(
2598 PVR2_TRACE_ERROR_LEGS,
2599 "Attempted to execute %d byte"
2600 " control-write transfer (limit=%d)",
2601 write_len,PVR2_CTL_BUFFSIZE);
2602 return -EINVAL;
2603 }
2604 if (read_len > PVR2_CTL_BUFFSIZE) {
2605 pvr2_trace(
2606 PVR2_TRACE_ERROR_LEGS,
2607 "Attempted to execute %d byte"
2608 " control-read transfer (limit=%d)",
2609 write_len,PVR2_CTL_BUFFSIZE);
2610 return -EINVAL;
2611 }
2612 if ((!write_len) && (!read_len)) {
2613 pvr2_trace(
2614 PVR2_TRACE_ERROR_LEGS,
2615 "Attempted to execute null control transfer?");
2616 return -EINVAL;
2617 }
2618
2619
2620 hdw->cmd_debug_state = 1;
2621 if (write_len) {
2622 hdw->cmd_debug_code = ((unsigned char *)write_data)[0];
2623 } else {
2624 hdw->cmd_debug_code = 0;
2625 }
2626 hdw->cmd_debug_write_len = write_len;
2627 hdw->cmd_debug_read_len = read_len;
2628
2629 /* Initialize common stuff */
2630 init_completion(&hdw->ctl_done);
2631 hdw->ctl_timeout_flag = 0;
2632 hdw->ctl_write_pend_flag = 0;
2633 hdw->ctl_read_pend_flag = 0;
2634 init_timer(&timer);
2635 timer.expires = jiffies + timeout;
2636 timer.data = (unsigned long)hdw;
2637 timer.function = pvr2_ctl_timeout;
2638
2639 if (write_len) {
2640 hdw->cmd_debug_state = 2;
2641 /* Transfer write data to internal buffer */
2642 for (idx = 0; idx < write_len; idx++) {
2643 hdw->ctl_write_buffer[idx] =
2644 ((unsigned char *)write_data)[idx];
2645 }
2646 /* Initiate a write request */
2647 usb_fill_bulk_urb(hdw->ctl_write_urb,
2648 hdw->usb_dev,
2649 usb_sndbulkpipe(hdw->usb_dev,
2650 PVR2_CTL_WRITE_ENDPOINT),
2651 hdw->ctl_write_buffer,
2652 write_len,
2653 pvr2_ctl_write_complete,
2654 hdw);
2655 hdw->ctl_write_urb->actual_length = 0;
2656 hdw->ctl_write_pend_flag = !0;
2657 status = usb_submit_urb(hdw->ctl_write_urb,GFP_KERNEL);
2658 if (status < 0) {
2659 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2660 "Failed to submit write-control"
2661 " URB status=%d",status);
2662 hdw->ctl_write_pend_flag = 0;
2663 goto done;
2664 }
2665 }
2666
2667 if (read_len) {
2668 hdw->cmd_debug_state = 3;
2669 memset(hdw->ctl_read_buffer,0x43,read_len);
2670 /* Initiate a read request */
2671 usb_fill_bulk_urb(hdw->ctl_read_urb,
2672 hdw->usb_dev,
2673 usb_rcvbulkpipe(hdw->usb_dev,
2674 PVR2_CTL_READ_ENDPOINT),
2675 hdw->ctl_read_buffer,
2676 read_len,
2677 pvr2_ctl_read_complete,
2678 hdw);
2679 hdw->ctl_read_urb->actual_length = 0;
2680 hdw->ctl_read_pend_flag = !0;
2681 status = usb_submit_urb(hdw->ctl_read_urb,GFP_KERNEL);
2682 if (status < 0) {
2683 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2684 "Failed to submit read-control"
2685 " URB status=%d",status);
2686 hdw->ctl_read_pend_flag = 0;
2687 goto done;
2688 }
2689 }
2690
2691 /* Start timer */
2692 add_timer(&timer);
2693
2694 /* Now wait for all I/O to complete */
2695 hdw->cmd_debug_state = 4;
2696 while (hdw->ctl_write_pend_flag || hdw->ctl_read_pend_flag) {
2697 wait_for_completion(&hdw->ctl_done);
2698 }
2699 hdw->cmd_debug_state = 5;
2700
2701 /* Stop timer */
2702 del_timer_sync(&timer);
2703
2704 hdw->cmd_debug_state = 6;
2705 status = 0;
2706
2707 if (hdw->ctl_timeout_flag) {
2708 status = -ETIMEDOUT;
2709 if (!probe_fl) {
2710 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2711 "Timed out control-write");
2712 }
2713 goto done;
2714 }
2715
2716 if (write_len) {
2717 /* Validate results of write request */
2718 if ((hdw->ctl_write_urb->status != 0) &&
2719 (hdw->ctl_write_urb->status != -ENOENT) &&
2720 (hdw->ctl_write_urb->status != -ESHUTDOWN) &&
2721 (hdw->ctl_write_urb->status != -ECONNRESET)) {
2722 /* USB subsystem is reporting some kind of failure
2723 on the write */
2724 status = hdw->ctl_write_urb->status;
2725 if (!probe_fl) {
2726 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2727 "control-write URB failure,"
2728 " status=%d",
2729 status);
2730 }
2731 goto done;
2732 }
2733 if (hdw->ctl_write_urb->actual_length < write_len) {
2734 /* Failed to write enough data */
2735 status = -EIO;
2736 if (!probe_fl) {
2737 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2738 "control-write URB short,"
2739 " expected=%d got=%d",
2740 write_len,
2741 hdw->ctl_write_urb->actual_length);
2742 }
2743 goto done;
2744 }
2745 }
2746 if (read_len) {
2747 /* Validate results of read request */
2748 if ((hdw->ctl_read_urb->status != 0) &&
2749 (hdw->ctl_read_urb->status != -ENOENT) &&
2750 (hdw->ctl_read_urb->status != -ESHUTDOWN) &&
2751 (hdw->ctl_read_urb->status != -ECONNRESET)) {
2752 /* USB subsystem is reporting some kind of failure
2753 on the read */
2754 status = hdw->ctl_read_urb->status;
2755 if (!probe_fl) {
2756 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2757 "control-read URB failure,"
2758 " status=%d",
2759 status);
2760 }
2761 goto done;
2762 }
2763 if (hdw->ctl_read_urb->actual_length < read_len) {
2764 /* Failed to read enough data */
2765 status = -EIO;
2766 if (!probe_fl) {
2767 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2768 "control-read URB short,"
2769 " expected=%d got=%d",
2770 read_len,
2771 hdw->ctl_read_urb->actual_length);
2772 }
2773 goto done;
2774 }
2775 /* Transfer retrieved data out from internal buffer */
2776 for (idx = 0; idx < read_len; idx++) {
2777 ((unsigned char *)read_data)[idx] =
2778 hdw->ctl_read_buffer[idx];
2779 }
2780 }
2781
2782 done:
2783
2784 hdw->cmd_debug_state = 0;
2785 if ((status < 0) && (!probe_fl)) {
2786 pvr2_hdw_render_useless_unlocked(hdw);
2787 }
2788 return status;
2789}
2790
2791
2792int pvr2_send_request(struct pvr2_hdw *hdw,
2793 void *write_data,unsigned int write_len,
2794 void *read_data,unsigned int read_len)
2795{
2796 return pvr2_send_request_ex(hdw,HZ*4,0,
2797 write_data,write_len,
2798 read_data,read_len);
2799}
2800
2801int pvr2_write_register(struct pvr2_hdw *hdw, u16 reg, u32 data)
2802{
2803 int ret;
2804
2805 LOCK_TAKE(hdw->ctl_lock);
2806
2807 hdw->cmd_buffer[0] = 0x04; /* write register prefix */
2808 PVR2_DECOMPOSE_LE(hdw->cmd_buffer,1,data);
2809 hdw->cmd_buffer[5] = 0;
2810 hdw->cmd_buffer[6] = (reg >> 8) & 0xff;
2811 hdw->cmd_buffer[7] = reg & 0xff;
2812
2813
2814 ret = pvr2_send_request(hdw, hdw->cmd_buffer, 8, hdw->cmd_buffer, 0);
2815
2816 LOCK_GIVE(hdw->ctl_lock);
2817
2818 return ret;
2819}
2820
2821
Adrian Bunk07e337e2006-06-30 11:30:20 -03002822static int pvr2_read_register(struct pvr2_hdw *hdw, u16 reg, u32 *data)
Mike Iselyd8554972006-06-26 20:58:46 -03002823{
2824 int ret = 0;
2825
2826 LOCK_TAKE(hdw->ctl_lock);
2827
2828 hdw->cmd_buffer[0] = 0x05; /* read register prefix */
2829 hdw->cmd_buffer[1] = 0;
2830 hdw->cmd_buffer[2] = 0;
2831 hdw->cmd_buffer[3] = 0;
2832 hdw->cmd_buffer[4] = 0;
2833 hdw->cmd_buffer[5] = 0;
2834 hdw->cmd_buffer[6] = (reg >> 8) & 0xff;
2835 hdw->cmd_buffer[7] = reg & 0xff;
2836
2837 ret |= pvr2_send_request(hdw, hdw->cmd_buffer, 8, hdw->cmd_buffer, 4);
2838 *data = PVR2_COMPOSE_LE(hdw->cmd_buffer,0);
2839
2840 LOCK_GIVE(hdw->ctl_lock);
2841
2842 return ret;
2843}
2844
2845
Adrian Bunk07e337e2006-06-30 11:30:20 -03002846static int pvr2_write_u16(struct pvr2_hdw *hdw, u16 data, int res)
Mike Iselyd8554972006-06-26 20:58:46 -03002847{
2848 int ret;
2849
2850 LOCK_TAKE(hdw->ctl_lock);
2851
2852 hdw->cmd_buffer[0] = (data >> 8) & 0xff;
2853 hdw->cmd_buffer[1] = data & 0xff;
2854
2855 ret = pvr2_send_request(hdw, hdw->cmd_buffer, 2, hdw->cmd_buffer, res);
2856
2857 LOCK_GIVE(hdw->ctl_lock);
2858
2859 return ret;
2860}
2861
2862
Adrian Bunk07e337e2006-06-30 11:30:20 -03002863static int pvr2_write_u8(struct pvr2_hdw *hdw, u8 data, int res)
Mike Iselyd8554972006-06-26 20:58:46 -03002864{
2865 int ret;
2866
2867 LOCK_TAKE(hdw->ctl_lock);
2868
2869 hdw->cmd_buffer[0] = data;
2870
2871 ret = pvr2_send_request(hdw, hdw->cmd_buffer, 1, hdw->cmd_buffer, res);
2872
2873 LOCK_GIVE(hdw->ctl_lock);
2874
2875 return ret;
2876}
2877
2878
Adrian Bunk07e337e2006-06-30 11:30:20 -03002879static void pvr2_hdw_render_useless_unlocked(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002880{
2881 if (!hdw->flag_ok) return;
2882 pvr2_trace(PVR2_TRACE_INIT,"render_useless");
2883 hdw->flag_ok = 0;
2884 if (hdw->vid_stream) {
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002885 pvr2_stream_setup(hdw->vid_stream,NULL,0,0);
Mike Iselyd8554972006-06-26 20:58:46 -03002886 }
2887 hdw->flag_streaming_enabled = 0;
2888 hdw->subsys_enabled_mask = 0;
2889}
2890
2891
2892void pvr2_hdw_render_useless(struct pvr2_hdw *hdw)
2893{
2894 LOCK_TAKE(hdw->ctl_lock);
2895 pvr2_hdw_render_useless_unlocked(hdw);
2896 LOCK_GIVE(hdw->ctl_lock);
2897}
2898
2899
2900void pvr2_hdw_device_reset(struct pvr2_hdw *hdw)
2901{
2902 int ret;
2903 pvr2_trace(PVR2_TRACE_INIT,"Performing a device reset...");
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002904 ret = usb_lock_device_for_reset(hdw->usb_dev,NULL);
Mike Iselyd8554972006-06-26 20:58:46 -03002905 if (ret == 1) {
2906 ret = usb_reset_device(hdw->usb_dev);
2907 usb_unlock_device(hdw->usb_dev);
2908 } else {
2909 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2910 "Failed to lock USB device ret=%d",ret);
2911 }
2912 if (init_pause_msec) {
2913 pvr2_trace(PVR2_TRACE_INFO,
2914 "Waiting %u msec for hardware to settle",
2915 init_pause_msec);
2916 msleep(init_pause_msec);
2917 }
2918
2919}
2920
2921
2922void pvr2_hdw_cpureset_assert(struct pvr2_hdw *hdw,int val)
2923{
2924 char da[1];
2925 unsigned int pipe;
2926 int ret;
2927
2928 if (!hdw->usb_dev) return;
2929
2930 pvr2_trace(PVR2_TRACE_INIT,"cpureset_assert(%d)",val);
2931
2932 da[0] = val ? 0x01 : 0x00;
2933
2934 /* Write the CPUCS register on the 8051. The lsb of the register
2935 is the reset bit; a 1 asserts reset while a 0 clears it. */
2936 pipe = usb_sndctrlpipe(hdw->usb_dev, 0);
2937 ret = usb_control_msg(hdw->usb_dev,pipe,0xa0,0x40,0xe600,0,da,1,HZ);
2938 if (ret < 0) {
2939 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2940 "cpureset_assert(%d) error=%d",val,ret);
2941 pvr2_hdw_render_useless(hdw);
2942 }
2943}
2944
2945
2946int pvr2_hdw_cmd_deep_reset(struct pvr2_hdw *hdw)
2947{
2948 int status;
2949 LOCK_TAKE(hdw->ctl_lock); do {
2950 pvr2_trace(PVR2_TRACE_INIT,"Requesting uproc hard reset");
2951 hdw->flag_ok = !0;
2952 hdw->cmd_buffer[0] = 0xdd;
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002953 status = pvr2_send_request(hdw,hdw->cmd_buffer,1,NULL,0);
Mike Iselyd8554972006-06-26 20:58:46 -03002954 } while (0); LOCK_GIVE(hdw->ctl_lock);
2955 return status;
2956}
2957
2958
2959int pvr2_hdw_cmd_powerup(struct pvr2_hdw *hdw)
2960{
2961 int status;
2962 LOCK_TAKE(hdw->ctl_lock); do {
2963 pvr2_trace(PVR2_TRACE_INIT,"Requesting powerup");
2964 hdw->cmd_buffer[0] = 0xde;
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002965 status = pvr2_send_request(hdw,hdw->cmd_buffer,1,NULL,0);
Mike Iselyd8554972006-06-26 20:58:46 -03002966 } while (0); LOCK_GIVE(hdw->ctl_lock);
2967 return status;
2968}
2969
2970
2971int pvr2_hdw_cmd_decoder_reset(struct pvr2_hdw *hdw)
2972{
2973 if (!hdw->decoder_ctrl) {
2974 pvr2_trace(PVR2_TRACE_INIT,
2975 "Unable to reset decoder: nothing attached");
2976 return -ENOTTY;
2977 }
2978
2979 if (!hdw->decoder_ctrl->force_reset) {
2980 pvr2_trace(PVR2_TRACE_INIT,
2981 "Unable to reset decoder: not implemented");
2982 return -ENOTTY;
2983 }
2984
2985 pvr2_trace(PVR2_TRACE_INIT,
2986 "Requesting decoder reset");
2987 hdw->decoder_ctrl->force_reset(hdw->decoder_ctrl->ctxt);
2988 return 0;
2989}
2990
2991
Mike Iselye61b6fc2006-07-18 22:42:18 -03002992/* Stop / start video stream transport */
Adrian Bunk07e337e2006-06-30 11:30:20 -03002993static int pvr2_hdw_cmd_usbstream(struct pvr2_hdw *hdw,int runFl)
Mike Iselyd8554972006-06-26 20:58:46 -03002994{
2995 int status;
2996 LOCK_TAKE(hdw->ctl_lock); do {
2997 hdw->cmd_buffer[0] = (runFl ? 0x36 : 0x37);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002998 status = pvr2_send_request(hdw,hdw->cmd_buffer,1,NULL,0);
Mike Iselyd8554972006-06-26 20:58:46 -03002999 } while (0); LOCK_GIVE(hdw->ctl_lock);
3000 if (!status) {
3001 hdw->subsys_enabled_mask =
3002 ((hdw->subsys_enabled_mask &
3003 ~(1<<PVR2_SUBSYS_B_USBSTREAM_RUN)) |
3004 (runFl ? (1<<PVR2_SUBSYS_B_USBSTREAM_RUN) : 0));
3005 }
3006 return status;
3007}
3008
3009
3010void pvr2_hdw_get_debug_info(const struct pvr2_hdw *hdw,
3011 struct pvr2_hdw_debug_info *ptr)
3012{
3013 ptr->big_lock_held = hdw->big_lock_held;
3014 ptr->ctl_lock_held = hdw->ctl_lock_held;
3015 ptr->flag_ok = hdw->flag_ok;
3016 ptr->flag_disconnected = hdw->flag_disconnected;
3017 ptr->flag_init_ok = hdw->flag_init_ok;
3018 ptr->flag_streaming_enabled = hdw->flag_streaming_enabled;
3019 ptr->subsys_flags = hdw->subsys_enabled_mask;
3020 ptr->cmd_debug_state = hdw->cmd_debug_state;
3021 ptr->cmd_code = hdw->cmd_debug_code;
3022 ptr->cmd_debug_write_len = hdw->cmd_debug_write_len;
3023 ptr->cmd_debug_read_len = hdw->cmd_debug_read_len;
3024 ptr->cmd_debug_timeout = hdw->ctl_timeout_flag;
3025 ptr->cmd_debug_write_pend = hdw->ctl_write_pend_flag;
3026 ptr->cmd_debug_read_pend = hdw->ctl_read_pend_flag;
3027 ptr->cmd_debug_rstatus = hdw->ctl_read_urb->status;
3028 ptr->cmd_debug_wstatus = hdw->ctl_read_urb->status;
3029}
3030
3031
3032int pvr2_hdw_gpio_get_dir(struct pvr2_hdw *hdw,u32 *dp)
3033{
3034 return pvr2_read_register(hdw,PVR2_GPIO_DIR,dp);
3035}
3036
3037
3038int pvr2_hdw_gpio_get_out(struct pvr2_hdw *hdw,u32 *dp)
3039{
3040 return pvr2_read_register(hdw,PVR2_GPIO_OUT,dp);
3041}
3042
3043
3044int pvr2_hdw_gpio_get_in(struct pvr2_hdw *hdw,u32 *dp)
3045{
3046 return pvr2_read_register(hdw,PVR2_GPIO_IN,dp);
3047}
3048
3049
3050int pvr2_hdw_gpio_chg_dir(struct pvr2_hdw *hdw,u32 msk,u32 val)
3051{
3052 u32 cval,nval;
3053 int ret;
3054 if (~msk) {
3055 ret = pvr2_read_register(hdw,PVR2_GPIO_DIR,&cval);
3056 if (ret) return ret;
3057 nval = (cval & ~msk) | (val & msk);
3058 pvr2_trace(PVR2_TRACE_GPIO,
3059 "GPIO direction changing 0x%x:0x%x"
3060 " from 0x%x to 0x%x",
3061 msk,val,cval,nval);
3062 } else {
3063 nval = val;
3064 pvr2_trace(PVR2_TRACE_GPIO,
3065 "GPIO direction changing to 0x%x",nval);
3066 }
3067 return pvr2_write_register(hdw,PVR2_GPIO_DIR,nval);
3068}
3069
3070
3071int pvr2_hdw_gpio_chg_out(struct pvr2_hdw *hdw,u32 msk,u32 val)
3072{
3073 u32 cval,nval;
3074 int ret;
3075 if (~msk) {
3076 ret = pvr2_read_register(hdw,PVR2_GPIO_OUT,&cval);
3077 if (ret) return ret;
3078 nval = (cval & ~msk) | (val & msk);
3079 pvr2_trace(PVR2_TRACE_GPIO,
3080 "GPIO output changing 0x%x:0x%x from 0x%x to 0x%x",
3081 msk,val,cval,nval);
3082 } else {
3083 nval = val;
3084 pvr2_trace(PVR2_TRACE_GPIO,
3085 "GPIO output changing to 0x%x",nval);
3086 }
3087 return pvr2_write_register(hdw,PVR2_GPIO_OUT,nval);
3088}
3089
3090
Mike Iselye61b6fc2006-07-18 22:42:18 -03003091/* Find I2C address of eeprom */
Adrian Bunk07e337e2006-06-30 11:30:20 -03003092static int pvr2_hdw_get_eeprom_addr(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03003093{
3094 int result;
3095 LOCK_TAKE(hdw->ctl_lock); do {
3096 hdw->cmd_buffer[0] = 0xeb;
3097 result = pvr2_send_request(hdw,
3098 hdw->cmd_buffer,1,
3099 hdw->cmd_buffer,1);
3100 if (result < 0) break;
3101 result = hdw->cmd_buffer[0];
3102 } while(0); LOCK_GIVE(hdw->ctl_lock);
3103 return result;
3104}
3105
3106
Mike Isely32ffa9a2006-09-23 22:26:52 -03003107int pvr2_hdw_register_access(struct pvr2_hdw *hdw,
3108 u32 chip_id,unsigned long reg_id,
3109 int setFl,u32 *val_ptr)
3110{
3111#ifdef CONFIG_VIDEO_ADV_DEBUG
3112 struct list_head *item;
3113 struct pvr2_i2c_client *cp;
3114 struct v4l2_register req;
Mike Isely6d988162006-09-28 17:53:49 -03003115 int stat = 0;
3116 int okFl = 0;
Mike Isely32ffa9a2006-09-23 22:26:52 -03003117
3118 req.i2c_id = chip_id;
3119 req.reg = reg_id;
3120 if (setFl) req.val = *val_ptr;
3121 mutex_lock(&hdw->i2c_list_lock); do {
3122 list_for_each(item,&hdw->i2c_clients) {
3123 cp = list_entry(item,struct pvr2_i2c_client,list);
3124 if (cp->client->driver->id != chip_id) continue;
3125 stat = pvr2_i2c_client_cmd(
3126 cp,(setFl ? VIDIOC_INT_S_REGISTER :
3127 VIDIOC_INT_G_REGISTER),&req);
3128 if (!setFl) *val_ptr = req.val;
Mike Isely6d988162006-09-28 17:53:49 -03003129 okFl = !0;
3130 break;
Mike Isely32ffa9a2006-09-23 22:26:52 -03003131 }
3132 } while (0); mutex_unlock(&hdw->i2c_list_lock);
Mike Isely6d988162006-09-28 17:53:49 -03003133 if (okFl) {
3134 return stat;
3135 }
Mike Isely32ffa9a2006-09-23 22:26:52 -03003136 return -EINVAL;
3137#else
3138 return -ENOSYS;
3139#endif
3140}
3141
3142
Mike Iselyd8554972006-06-26 20:58:46 -03003143/*
3144 Stuff for Emacs to see, in order to encourage consistent editing style:
3145 *** Local Variables: ***
3146 *** mode: c ***
3147 *** fill-column: 75 ***
3148 *** tab-width: 8 ***
3149 *** c-basic-offset: 8 ***
3150 *** End: ***
3151 */