blob: 37364b072e7b2c71c2d46f828013d8c40c1603e4 [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 Iselyd8554972006-06-26 20:58:46 -030028#include "pvrusb2.h"
29#include "pvrusb2-std.h"
30#include "pvrusb2-util.h"
31#include "pvrusb2-hdw.h"
32#include "pvrusb2-i2c-core.h"
33#include "pvrusb2-tuner.h"
34#include "pvrusb2-eeprom.h"
35#include "pvrusb2-hdw-internal.h"
36#include "pvrusb2-encoder.h"
37#include "pvrusb2-debug.h"
Michael Krufky8d364362007-01-22 02:17:55 -030038#include "pvrusb2-fx2-cmd.h"
Mike Iselyd8554972006-06-26 20:58:46 -030039
Mike Isely1bde0282006-12-27 23:30:13 -030040#define TV_MIN_FREQ 55250000L
41#define TV_MAX_FREQ 850000000L
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -030042
Mike Iselya0fd1cb2006-06-30 11:35:28 -030043static struct pvr2_hdw *unit_pointers[PVR_NUM] = {[ 0 ... PVR_NUM-1 ] = NULL};
Matthias Kaehlcke8df0c872007-04-28 20:00:18 -030044static DEFINE_MUTEX(pvr2_unit_mtx);
Mike Iselyd8554972006-06-26 20:58:46 -030045
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -030046static int ctlchg;
Mike Iselyd8554972006-06-26 20:58:46 -030047static int initusbreset = 1;
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -030048static int procreload;
Mike Iselyd8554972006-06-26 20:58:46 -030049static int tuner[PVR_NUM] = { [0 ... PVR_NUM-1] = -1 };
50static int tolerance[PVR_NUM] = { [0 ... PVR_NUM-1] = 0 };
51static int video_std[PVR_NUM] = { [0 ... PVR_NUM-1] = 0 };
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -030052static int init_pause_msec;
Mike Iselyd8554972006-06-26 20:58:46 -030053
54module_param(ctlchg, int, S_IRUGO|S_IWUSR);
55MODULE_PARM_DESC(ctlchg, "0=optimize ctl change 1=always accept new ctl value");
56module_param(init_pause_msec, int, S_IRUGO|S_IWUSR);
57MODULE_PARM_DESC(init_pause_msec, "hardware initialization settling delay");
58module_param(initusbreset, int, S_IRUGO|S_IWUSR);
59MODULE_PARM_DESC(initusbreset, "Do USB reset device on probe");
60module_param(procreload, int, S_IRUGO|S_IWUSR);
61MODULE_PARM_DESC(procreload,
62 "Attempt init failure recovery with firmware reload");
63module_param_array(tuner, int, NULL, 0444);
64MODULE_PARM_DESC(tuner,"specify installed tuner type");
65module_param_array(video_std, int, NULL, 0444);
66MODULE_PARM_DESC(video_std,"specify initial video standard");
67module_param_array(tolerance, int, NULL, 0444);
68MODULE_PARM_DESC(tolerance,"specify stream error tolerance");
69
70#define PVR2_CTL_WRITE_ENDPOINT 0x01
71#define PVR2_CTL_READ_ENDPOINT 0x81
72
73#define PVR2_GPIO_IN 0x9008
74#define PVR2_GPIO_OUT 0x900c
75#define PVR2_GPIO_DIR 0x9020
76
77#define trace_firmware(...) pvr2_trace(PVR2_TRACE_FIRMWARE,__VA_ARGS__)
78
79#define PVR2_FIRMWARE_ENDPOINT 0x02
80
81/* size of a firmware chunk */
82#define FIRMWARE_CHUNK_SIZE 0x2000
83
Mike Iselyb30d2442006-06-25 20:05:01 -030084/* Define the list of additional controls we'll dynamically construct based
85 on query of the cx2341x module. */
86struct pvr2_mpeg_ids {
87 const char *strid;
88 int id;
89};
90static const struct pvr2_mpeg_ids mpeg_ids[] = {
91 {
92 .strid = "audio_layer",
93 .id = V4L2_CID_MPEG_AUDIO_ENCODING,
94 },{
95 .strid = "audio_bitrate",
96 .id = V4L2_CID_MPEG_AUDIO_L2_BITRATE,
97 },{
98 /* Already using audio_mode elsewhere :-( */
99 .strid = "mpeg_audio_mode",
100 .id = V4L2_CID_MPEG_AUDIO_MODE,
101 },{
102 .strid = "mpeg_audio_mode_extension",
103 .id = V4L2_CID_MPEG_AUDIO_MODE_EXTENSION,
104 },{
105 .strid = "audio_emphasis",
106 .id = V4L2_CID_MPEG_AUDIO_EMPHASIS,
107 },{
108 .strid = "audio_crc",
109 .id = V4L2_CID_MPEG_AUDIO_CRC,
110 },{
111 .strid = "video_aspect",
112 .id = V4L2_CID_MPEG_VIDEO_ASPECT,
113 },{
114 .strid = "video_b_frames",
115 .id = V4L2_CID_MPEG_VIDEO_B_FRAMES,
116 },{
117 .strid = "video_gop_size",
118 .id = V4L2_CID_MPEG_VIDEO_GOP_SIZE,
119 },{
120 .strid = "video_gop_closure",
121 .id = V4L2_CID_MPEG_VIDEO_GOP_CLOSURE,
122 },{
Mike Iselyb30d2442006-06-25 20:05:01 -0300123 .strid = "video_bitrate_mode",
124 .id = V4L2_CID_MPEG_VIDEO_BITRATE_MODE,
125 },{
126 .strid = "video_bitrate",
127 .id = V4L2_CID_MPEG_VIDEO_BITRATE,
128 },{
129 .strid = "video_bitrate_peak",
130 .id = V4L2_CID_MPEG_VIDEO_BITRATE_PEAK,
131 },{
132 .strid = "video_temporal_decimation",
133 .id = V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION,
134 },{
135 .strid = "stream_type",
136 .id = V4L2_CID_MPEG_STREAM_TYPE,
137 },{
138 .strid = "video_spatial_filter_mode",
139 .id = V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE,
140 },{
141 .strid = "video_spatial_filter",
142 .id = V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER,
143 },{
144 .strid = "video_luma_spatial_filter_type",
145 .id = V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE,
146 },{
147 .strid = "video_chroma_spatial_filter_type",
148 .id = V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE,
149 },{
150 .strid = "video_temporal_filter_mode",
151 .id = V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE,
152 },{
153 .strid = "video_temporal_filter",
154 .id = V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER,
155 },{
156 .strid = "video_median_filter_type",
157 .id = V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE,
158 },{
159 .strid = "video_luma_median_filter_top",
160 .id = V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP,
161 },{
162 .strid = "video_luma_median_filter_bottom",
163 .id = V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM,
164 },{
165 .strid = "video_chroma_median_filter_top",
166 .id = V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP,
167 },{
168 .strid = "video_chroma_median_filter_bottom",
169 .id = V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM,
170 }
171};
Ahmed S. Darwisheca8ebf2007-01-20 00:35:03 -0300172#define MPEGDEF_COUNT ARRAY_SIZE(mpeg_ids)
Mike Iselyc05c0462006-06-25 20:04:25 -0300173
Mike Iselyd8554972006-06-26 20:58:46 -0300174
Mike Isely434449f2006-08-08 09:10:06 -0300175static const char *control_values_srate[] = {
176 [V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100] = "44.1 kHz",
177 [V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000] = "48 kHz",
178 [V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000] = "32 kHz",
179};
Mike Iselyd8554972006-06-26 20:58:46 -0300180
Mike Iselyd8554972006-06-26 20:58:46 -0300181
182
183static const char *control_values_input[] = {
184 [PVR2_CVAL_INPUT_TV] = "television", /*xawtv needs this name*/
Mike Isely29bf5b12008-04-22 14:45:37 -0300185 [PVR2_CVAL_INPUT_DTV] = "dtv",
Mike Iselyd8554972006-06-26 20:58:46 -0300186 [PVR2_CVAL_INPUT_RADIO] = "radio",
187 [PVR2_CVAL_INPUT_SVIDEO] = "s-video",
188 [PVR2_CVAL_INPUT_COMPOSITE] = "composite",
189};
190
191
192static const char *control_values_audiomode[] = {
193 [V4L2_TUNER_MODE_MONO] = "Mono",
194 [V4L2_TUNER_MODE_STEREO] = "Stereo",
195 [V4L2_TUNER_MODE_LANG1] = "Lang1",
196 [V4L2_TUNER_MODE_LANG2] = "Lang2",
197 [V4L2_TUNER_MODE_LANG1_LANG2] = "Lang1+Lang2",
198};
199
200
201static const char *control_values_hsm[] = {
202 [PVR2_CVAL_HSM_FAIL] = "Fail",
203 [PVR2_CVAL_HSM_HIGH] = "High",
204 [PVR2_CVAL_HSM_FULL] = "Full",
205};
206
207
Mike Isely681c7392007-11-26 01:48:52 -0300208static const char *pvr2_state_names[] = {
209 [PVR2_STATE_NONE] = "none",
210 [PVR2_STATE_DEAD] = "dead",
211 [PVR2_STATE_COLD] = "cold",
212 [PVR2_STATE_WARM] = "warm",
213 [PVR2_STATE_ERROR] = "error",
214 [PVR2_STATE_READY] = "ready",
215 [PVR2_STATE_RUN] = "run",
Mike Iselyd8554972006-06-26 20:58:46 -0300216};
217
Mike Isely681c7392007-11-26 01:48:52 -0300218
Mike Isely694dca2b2008-03-28 05:42:10 -0300219struct pvr2_fx2cmd_descdef {
Mike Isely1c9d10d2008-03-28 05:38:54 -0300220 unsigned char id;
221 unsigned char *desc;
222};
223
Mike Isely694dca2b2008-03-28 05:42:10 -0300224static const struct pvr2_fx2cmd_descdef pvr2_fx2cmd_desc[] = {
Mike Isely1c9d10d2008-03-28 05:38:54 -0300225 {FX2CMD_MEM_WRITE_DWORD, "write encoder dword"},
226 {FX2CMD_MEM_READ_DWORD, "read encoder dword"},
227 {FX2CMD_MEM_READ_64BYTES, "read encoder 64bytes"},
228 {FX2CMD_REG_WRITE, "write encoder register"},
229 {FX2CMD_REG_READ, "read encoder register"},
230 {FX2CMD_MEMSEL, "encoder memsel"},
231 {FX2CMD_I2C_WRITE, "i2c write"},
232 {FX2CMD_I2C_READ, "i2c read"},
233 {FX2CMD_GET_USB_SPEED, "get USB speed"},
234 {FX2CMD_STREAMING_ON, "stream on"},
235 {FX2CMD_STREAMING_OFF, "stream off"},
236 {FX2CMD_FWPOST1, "fwpost1"},
237 {FX2CMD_POWER_OFF, "power off"},
238 {FX2CMD_POWER_ON, "power on"},
239 {FX2CMD_DEEP_RESET, "deep reset"},
240 {FX2CMD_GET_EEPROM_ADDR, "get rom addr"},
241 {FX2CMD_GET_IR_CODE, "get IR code"},
242 {FX2CMD_HCW_DEMOD_RESETIN, "hcw demod resetin"},
243 {FX2CMD_HCW_DTV_STREAMING_ON, "hcw dtv stream on"},
244 {FX2CMD_HCW_DTV_STREAMING_OFF, "hcw dtv stream off"},
245 {FX2CMD_ONAIR_DTV_STREAMING_ON, "onair dtv stream on"},
246 {FX2CMD_ONAIR_DTV_STREAMING_OFF, "onair dtv stream off"},
247 {FX2CMD_ONAIR_DTV_POWER_ON, "onair dtv power on"},
248 {FX2CMD_ONAIR_DTV_POWER_OFF, "onair dtv power off"},
249};
250
251
Mike Isely1cb03b72008-04-21 03:47:43 -0300252static int pvr2_hdw_set_input(struct pvr2_hdw *hdw,int v);
Mike Isely681c7392007-11-26 01:48:52 -0300253static void pvr2_hdw_state_sched(struct pvr2_hdw *);
254static int pvr2_hdw_state_eval(struct pvr2_hdw *);
Mike Isely1bde0282006-12-27 23:30:13 -0300255static void pvr2_hdw_set_cur_freq(struct pvr2_hdw *,unsigned long);
Mike Isely681c7392007-11-26 01:48:52 -0300256static void pvr2_hdw_worker_i2c(struct work_struct *work);
257static void pvr2_hdw_worker_poll(struct work_struct *work);
Mike Isely681c7392007-11-26 01:48:52 -0300258static int pvr2_hdw_wait(struct pvr2_hdw *,int state);
259static int pvr2_hdw_untrip_unlocked(struct pvr2_hdw *);
260static void pvr2_hdw_state_log_state(struct pvr2_hdw *);
Adrian Bunk07e337e2006-06-30 11:30:20 -0300261static int pvr2_hdw_cmd_usbstream(struct pvr2_hdw *hdw,int runFl);
Mike Isely681c7392007-11-26 01:48:52 -0300262static int pvr2_hdw_commit_setup(struct pvr2_hdw *hdw);
Adrian Bunk07e337e2006-06-30 11:30:20 -0300263static int pvr2_hdw_get_eeprom_addr(struct pvr2_hdw *hdw);
Adrian Bunk07e337e2006-06-30 11:30:20 -0300264static void pvr2_hdw_internal_find_stdenum(struct pvr2_hdw *hdw);
265static void pvr2_hdw_internal_set_std_avail(struct pvr2_hdw *hdw);
Mike Isely681c7392007-11-26 01:48:52 -0300266static void pvr2_hdw_quiescent_timeout(unsigned long);
267static void pvr2_hdw_encoder_wait_timeout(unsigned long);
Mike Iselyd913d632008-04-06 04:04:35 -0300268static void pvr2_hdw_encoder_run_timeout(unsigned long);
Mike Isely1c9d10d2008-03-28 05:38:54 -0300269static int pvr2_issue_simple_cmd(struct pvr2_hdw *,u32);
Adrian Bunk07e337e2006-06-30 11:30:20 -0300270static int pvr2_send_request_ex(struct pvr2_hdw *hdw,
271 unsigned int timeout,int probe_fl,
272 void *write_data,unsigned int write_len,
273 void *read_data,unsigned int read_len);
Mike Iselyd8554972006-06-26 20:58:46 -0300274
Mike Isely681c7392007-11-26 01:48:52 -0300275
276static void trace_stbit(const char *name,int val)
277{
278 pvr2_trace(PVR2_TRACE_STBITS,
279 "State bit %s <-- %s",
280 name,(val ? "true" : "false"));
281}
282
Mike Iselyd8554972006-06-26 20:58:46 -0300283static int ctrl_channelfreq_get(struct pvr2_ctrl *cptr,int *vp)
284{
285 struct pvr2_hdw *hdw = cptr->hdw;
286 if ((hdw->freqProgSlot > 0) && (hdw->freqProgSlot <= FREQTABLE_SIZE)) {
287 *vp = hdw->freqTable[hdw->freqProgSlot-1];
288 } else {
289 *vp = 0;
290 }
291 return 0;
292}
293
294static int ctrl_channelfreq_set(struct pvr2_ctrl *cptr,int m,int v)
295{
296 struct pvr2_hdw *hdw = cptr->hdw;
Mike Isely1bde0282006-12-27 23:30:13 -0300297 unsigned int slotId = hdw->freqProgSlot;
298 if ((slotId > 0) && (slotId <= FREQTABLE_SIZE)) {
299 hdw->freqTable[slotId-1] = v;
300 /* Handle side effects correctly - if we're tuned to this
301 slot, then forgot the slot id relation since the stored
302 frequency has been changed. */
303 if (hdw->freqSelector) {
304 if (hdw->freqSlotRadio == slotId) {
305 hdw->freqSlotRadio = 0;
306 }
307 } else {
308 if (hdw->freqSlotTelevision == slotId) {
309 hdw->freqSlotTelevision = 0;
310 }
311 }
Mike Iselyd8554972006-06-26 20:58:46 -0300312 }
313 return 0;
314}
315
316static int ctrl_channelprog_get(struct pvr2_ctrl *cptr,int *vp)
317{
318 *vp = cptr->hdw->freqProgSlot;
319 return 0;
320}
321
322static int ctrl_channelprog_set(struct pvr2_ctrl *cptr,int m,int v)
323{
324 struct pvr2_hdw *hdw = cptr->hdw;
325 if ((v >= 0) && (v <= FREQTABLE_SIZE)) {
326 hdw->freqProgSlot = v;
327 }
328 return 0;
329}
330
331static int ctrl_channel_get(struct pvr2_ctrl *cptr,int *vp)
332{
Mike Isely1bde0282006-12-27 23:30:13 -0300333 struct pvr2_hdw *hdw = cptr->hdw;
334 *vp = hdw->freqSelector ? hdw->freqSlotRadio : hdw->freqSlotTelevision;
Mike Iselyd8554972006-06-26 20:58:46 -0300335 return 0;
336}
337
Mike Isely1bde0282006-12-27 23:30:13 -0300338static int ctrl_channel_set(struct pvr2_ctrl *cptr,int m,int slotId)
Mike Iselyd8554972006-06-26 20:58:46 -0300339{
340 unsigned freq = 0;
341 struct pvr2_hdw *hdw = cptr->hdw;
Mike Isely1bde0282006-12-27 23:30:13 -0300342 if ((slotId < 0) || (slotId > FREQTABLE_SIZE)) return 0;
343 if (slotId > 0) {
344 freq = hdw->freqTable[slotId-1];
345 if (!freq) return 0;
346 pvr2_hdw_set_cur_freq(hdw,freq);
Mike Iselyd8554972006-06-26 20:58:46 -0300347 }
Mike Isely1bde0282006-12-27 23:30:13 -0300348 if (hdw->freqSelector) {
349 hdw->freqSlotRadio = slotId;
350 } else {
351 hdw->freqSlotTelevision = slotId;
Mike Iselyd8554972006-06-26 20:58:46 -0300352 }
353 return 0;
354}
355
356static int ctrl_freq_get(struct pvr2_ctrl *cptr,int *vp)
357{
Mike Isely1bde0282006-12-27 23:30:13 -0300358 *vp = pvr2_hdw_get_cur_freq(cptr->hdw);
Mike Iselyd8554972006-06-26 20:58:46 -0300359 return 0;
360}
361
362static int ctrl_freq_is_dirty(struct pvr2_ctrl *cptr)
363{
364 return cptr->hdw->freqDirty != 0;
365}
366
367static void ctrl_freq_clear_dirty(struct pvr2_ctrl *cptr)
368{
369 cptr->hdw->freqDirty = 0;
370}
371
372static int ctrl_freq_set(struct pvr2_ctrl *cptr,int m,int v)
373{
Mike Isely1bde0282006-12-27 23:30:13 -0300374 pvr2_hdw_set_cur_freq(cptr->hdw,v);
Mike Iselyd8554972006-06-26 20:58:46 -0300375 return 0;
376}
377
Mike Isely3ad9fc32006-09-02 22:37:52 -0300378static int ctrl_vres_max_get(struct pvr2_ctrl *cptr,int *vp)
379{
380 /* Actual maximum depends on the video standard in effect. */
381 if (cptr->hdw->std_mask_cur & V4L2_STD_525_60) {
382 *vp = 480;
383 } else {
384 *vp = 576;
385 }
386 return 0;
387}
388
389static int ctrl_vres_min_get(struct pvr2_ctrl *cptr,int *vp)
390{
Mike Isely989eb152007-11-26 01:53:12 -0300391 /* Actual minimum depends on device digitizer type. */
392 if (cptr->hdw->hdw_desc->flag_has_cx25840) {
Mike Isely3ad9fc32006-09-02 22:37:52 -0300393 *vp = 75;
394 } else {
395 *vp = 17;
396 }
397 return 0;
398}
399
Mike Isely1bde0282006-12-27 23:30:13 -0300400static int ctrl_get_input(struct pvr2_ctrl *cptr,int *vp)
401{
402 *vp = cptr->hdw->input_val;
403 return 0;
404}
405
Mike Isely29bf5b12008-04-22 14:45:37 -0300406static int ctrl_check_input(struct pvr2_ctrl *cptr,int v)
407{
Mike Isely1cb03b72008-04-21 03:47:43 -0300408 return ((1 << v) & cptr->hdw->input_allowed_mask) != 0;
Mike Isely29bf5b12008-04-22 14:45:37 -0300409}
410
Mike Isely1bde0282006-12-27 23:30:13 -0300411static int ctrl_set_input(struct pvr2_ctrl *cptr,int m,int v)
412{
Mike Isely1cb03b72008-04-21 03:47:43 -0300413 return pvr2_hdw_set_input(cptr->hdw,v);
Mike Isely1bde0282006-12-27 23:30:13 -0300414}
415
416static int ctrl_isdirty_input(struct pvr2_ctrl *cptr)
417{
418 return cptr->hdw->input_dirty != 0;
419}
420
421static void ctrl_cleardirty_input(struct pvr2_ctrl *cptr)
422{
423 cptr->hdw->input_dirty = 0;
424}
425
Mike Isely5549f542006-12-27 23:28:54 -0300426
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -0300427static int ctrl_freq_max_get(struct pvr2_ctrl *cptr, int *vp)
428{
Mike Isely644afdb2007-01-20 00:19:23 -0300429 unsigned long fv;
430 struct pvr2_hdw *hdw = cptr->hdw;
431 if (hdw->tuner_signal_stale) {
432 pvr2_i2c_core_status_poll(hdw);
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -0300433 }
Mike Isely644afdb2007-01-20 00:19:23 -0300434 fv = hdw->tuner_signal_info.rangehigh;
435 if (!fv) {
436 /* Safety fallback */
437 *vp = TV_MAX_FREQ;
438 return 0;
439 }
440 if (hdw->tuner_signal_info.capability & V4L2_TUNER_CAP_LOW) {
441 fv = (fv * 125) / 2;
442 } else {
443 fv = fv * 62500;
444 }
445 *vp = fv;
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -0300446 return 0;
447}
448
449static int ctrl_freq_min_get(struct pvr2_ctrl *cptr, int *vp)
450{
Mike Isely644afdb2007-01-20 00:19:23 -0300451 unsigned long fv;
452 struct pvr2_hdw *hdw = cptr->hdw;
453 if (hdw->tuner_signal_stale) {
454 pvr2_i2c_core_status_poll(hdw);
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -0300455 }
Mike Isely644afdb2007-01-20 00:19:23 -0300456 fv = hdw->tuner_signal_info.rangelow;
457 if (!fv) {
458 /* Safety fallback */
459 *vp = TV_MIN_FREQ;
460 return 0;
461 }
462 if (hdw->tuner_signal_info.capability & V4L2_TUNER_CAP_LOW) {
463 fv = (fv * 125) / 2;
464 } else {
465 fv = fv * 62500;
466 }
467 *vp = fv;
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -0300468 return 0;
469}
470
Mike Iselyb30d2442006-06-25 20:05:01 -0300471static int ctrl_cx2341x_is_dirty(struct pvr2_ctrl *cptr)
472{
473 return cptr->hdw->enc_stale != 0;
474}
475
476static void ctrl_cx2341x_clear_dirty(struct pvr2_ctrl *cptr)
477{
478 cptr->hdw->enc_stale = 0;
Mike Isely681c7392007-11-26 01:48:52 -0300479 cptr->hdw->enc_unsafe_stale = 0;
Mike Iselyb30d2442006-06-25 20:05:01 -0300480}
481
482static int ctrl_cx2341x_get(struct pvr2_ctrl *cptr,int *vp)
483{
484 int ret;
485 struct v4l2_ext_controls cs;
486 struct v4l2_ext_control c1;
487 memset(&cs,0,sizeof(cs));
488 memset(&c1,0,sizeof(c1));
489 cs.controls = &c1;
490 cs.count = 1;
491 c1.id = cptr->info->v4l_id;
Hans Verkuil01f1e442007-08-21 18:32:42 -0300492 ret = cx2341x_ext_ctrls(&cptr->hdw->enc_ctl_state, 0, &cs,
Mike Iselyb30d2442006-06-25 20:05:01 -0300493 VIDIOC_G_EXT_CTRLS);
494 if (ret) return ret;
495 *vp = c1.value;
496 return 0;
497}
498
499static int ctrl_cx2341x_set(struct pvr2_ctrl *cptr,int m,int v)
500{
501 int ret;
Mike Isely681c7392007-11-26 01:48:52 -0300502 struct pvr2_hdw *hdw = cptr->hdw;
Mike Iselyb30d2442006-06-25 20:05:01 -0300503 struct v4l2_ext_controls cs;
504 struct v4l2_ext_control c1;
505 memset(&cs,0,sizeof(cs));
506 memset(&c1,0,sizeof(c1));
507 cs.controls = &c1;
508 cs.count = 1;
509 c1.id = cptr->info->v4l_id;
510 c1.value = v;
Mike Isely681c7392007-11-26 01:48:52 -0300511 ret = cx2341x_ext_ctrls(&hdw->enc_ctl_state,
512 hdw->state_encoder_run, &cs,
Mike Iselyb30d2442006-06-25 20:05:01 -0300513 VIDIOC_S_EXT_CTRLS);
Mike Isely681c7392007-11-26 01:48:52 -0300514 if (ret == -EBUSY) {
515 /* Oops. cx2341x is telling us it's not safe to change
516 this control while we're capturing. Make a note of this
517 fact so that the pipeline will be stopped the next time
518 controls are committed. Then go on ahead and store this
519 change anyway. */
520 ret = cx2341x_ext_ctrls(&hdw->enc_ctl_state,
521 0, &cs,
522 VIDIOC_S_EXT_CTRLS);
523 if (!ret) hdw->enc_unsafe_stale = !0;
524 }
Mike Iselyb30d2442006-06-25 20:05:01 -0300525 if (ret) return ret;
Mike Isely681c7392007-11-26 01:48:52 -0300526 hdw->enc_stale = !0;
Mike Iselyb30d2442006-06-25 20:05:01 -0300527 return 0;
528}
529
530static unsigned int ctrl_cx2341x_getv4lflags(struct pvr2_ctrl *cptr)
531{
532 struct v4l2_queryctrl qctrl;
533 struct pvr2_ctl_info *info;
534 qctrl.id = cptr->info->v4l_id;
535 cx2341x_ctrl_query(&cptr->hdw->enc_ctl_state,&qctrl);
536 /* Strip out the const so we can adjust a function pointer. It's
537 OK to do this here because we know this is a dynamically created
538 control, so the underlying storage for the info pointer is (a)
539 private to us, and (b) not in read-only storage. Either we do
540 this or we significantly complicate the underlying control
541 implementation. */
542 info = (struct pvr2_ctl_info *)(cptr->info);
543 if (qctrl.flags & V4L2_CTRL_FLAG_READ_ONLY) {
544 if (info->set_value) {
Mike Iselya0fd1cb2006-06-30 11:35:28 -0300545 info->set_value = NULL;
Mike Iselyb30d2442006-06-25 20:05:01 -0300546 }
547 } else {
548 if (!(info->set_value)) {
549 info->set_value = ctrl_cx2341x_set;
550 }
551 }
552 return qctrl.flags;
553}
554
Mike Iselyd8554972006-06-26 20:58:46 -0300555static int ctrl_streamingenabled_get(struct pvr2_ctrl *cptr,int *vp)
556{
Mike Isely681c7392007-11-26 01:48:52 -0300557 *vp = cptr->hdw->state_pipeline_req;
558 return 0;
559}
560
561static int ctrl_masterstate_get(struct pvr2_ctrl *cptr,int *vp)
562{
563 *vp = cptr->hdw->master_state;
Mike Iselyd8554972006-06-26 20:58:46 -0300564 return 0;
565}
566
567static int ctrl_hsm_get(struct pvr2_ctrl *cptr,int *vp)
568{
569 int result = pvr2_hdw_is_hsm(cptr->hdw);
570 *vp = PVR2_CVAL_HSM_FULL;
571 if (result < 0) *vp = PVR2_CVAL_HSM_FAIL;
572 if (result) *vp = PVR2_CVAL_HSM_HIGH;
573 return 0;
574}
575
576static int ctrl_stdavail_get(struct pvr2_ctrl *cptr,int *vp)
577{
578 *vp = cptr->hdw->std_mask_avail;
579 return 0;
580}
581
582static int ctrl_stdavail_set(struct pvr2_ctrl *cptr,int m,int v)
583{
584 struct pvr2_hdw *hdw = cptr->hdw;
585 v4l2_std_id ns;
586 ns = hdw->std_mask_avail;
587 ns = (ns & ~m) | (v & m);
588 if (ns == hdw->std_mask_avail) return 0;
589 hdw->std_mask_avail = ns;
590 pvr2_hdw_internal_set_std_avail(hdw);
591 pvr2_hdw_internal_find_stdenum(hdw);
592 return 0;
593}
594
595static int ctrl_std_val_to_sym(struct pvr2_ctrl *cptr,int msk,int val,
596 char *bufPtr,unsigned int bufSize,
597 unsigned int *len)
598{
599 *len = pvr2_std_id_to_str(bufPtr,bufSize,msk & val);
600 return 0;
601}
602
603static int ctrl_std_sym_to_val(struct pvr2_ctrl *cptr,
604 const char *bufPtr,unsigned int bufSize,
605 int *mskp,int *valp)
606{
607 int ret;
608 v4l2_std_id id;
609 ret = pvr2_std_str_to_id(&id,bufPtr,bufSize);
610 if (ret < 0) return ret;
611 if (mskp) *mskp = id;
612 if (valp) *valp = id;
613 return 0;
614}
615
616static int ctrl_stdcur_get(struct pvr2_ctrl *cptr,int *vp)
617{
618 *vp = cptr->hdw->std_mask_cur;
619 return 0;
620}
621
622static int ctrl_stdcur_set(struct pvr2_ctrl *cptr,int m,int v)
623{
624 struct pvr2_hdw *hdw = cptr->hdw;
625 v4l2_std_id ns;
626 ns = hdw->std_mask_cur;
627 ns = (ns & ~m) | (v & m);
628 if (ns == hdw->std_mask_cur) return 0;
629 hdw->std_mask_cur = ns;
630 hdw->std_dirty = !0;
631 pvr2_hdw_internal_find_stdenum(hdw);
632 return 0;
633}
634
635static int ctrl_stdcur_is_dirty(struct pvr2_ctrl *cptr)
636{
637 return cptr->hdw->std_dirty != 0;
638}
639
640static void ctrl_stdcur_clear_dirty(struct pvr2_ctrl *cptr)
641{
642 cptr->hdw->std_dirty = 0;
643}
644
645static int ctrl_signal_get(struct pvr2_ctrl *cptr,int *vp)
646{
Mike Isely18103c572007-01-20 00:09:47 -0300647 struct pvr2_hdw *hdw = cptr->hdw;
648 pvr2_i2c_core_status_poll(hdw);
649 *vp = hdw->tuner_signal_info.signal;
650 return 0;
651}
652
653static int ctrl_audio_modes_present_get(struct pvr2_ctrl *cptr,int *vp)
654{
655 int val = 0;
656 unsigned int subchan;
657 struct pvr2_hdw *hdw = cptr->hdw;
Mike Isely644afdb2007-01-20 00:19:23 -0300658 pvr2_i2c_core_status_poll(hdw);
Mike Isely18103c572007-01-20 00:09:47 -0300659 subchan = hdw->tuner_signal_info.rxsubchans;
660 if (subchan & V4L2_TUNER_SUB_MONO) {
661 val |= (1 << V4L2_TUNER_MODE_MONO);
662 }
663 if (subchan & V4L2_TUNER_SUB_STEREO) {
664 val |= (1 << V4L2_TUNER_MODE_STEREO);
665 }
666 if (subchan & V4L2_TUNER_SUB_LANG1) {
667 val |= (1 << V4L2_TUNER_MODE_LANG1);
668 }
669 if (subchan & V4L2_TUNER_SUB_LANG2) {
670 val |= (1 << V4L2_TUNER_MODE_LANG2);
671 }
672 *vp = val;
Mike Iselyd8554972006-06-26 20:58:46 -0300673 return 0;
674}
675
Mike Iselyd8554972006-06-26 20:58:46 -0300676
677static int ctrl_stdenumcur_set(struct pvr2_ctrl *cptr,int m,int v)
678{
679 struct pvr2_hdw *hdw = cptr->hdw;
680 if (v < 0) return -EINVAL;
681 if (v > hdw->std_enum_cnt) return -EINVAL;
682 hdw->std_enum_cur = v;
683 if (!v) return 0;
684 v--;
685 if (hdw->std_mask_cur == hdw->std_defs[v].id) return 0;
686 hdw->std_mask_cur = hdw->std_defs[v].id;
687 hdw->std_dirty = !0;
688 return 0;
689}
690
691
692static int ctrl_stdenumcur_get(struct pvr2_ctrl *cptr,int *vp)
693{
694 *vp = cptr->hdw->std_enum_cur;
695 return 0;
696}
697
698
699static int ctrl_stdenumcur_is_dirty(struct pvr2_ctrl *cptr)
700{
701 return cptr->hdw->std_dirty != 0;
702}
703
704
705static void ctrl_stdenumcur_clear_dirty(struct pvr2_ctrl *cptr)
706{
707 cptr->hdw->std_dirty = 0;
708}
709
710
711#define DEFINT(vmin,vmax) \
712 .type = pvr2_ctl_int, \
713 .def.type_int.min_value = vmin, \
714 .def.type_int.max_value = vmax
715
716#define DEFENUM(tab) \
717 .type = pvr2_ctl_enum, \
Mike Isely27c7b712007-01-20 00:39:17 -0300718 .def.type_enum.count = ARRAY_SIZE(tab), \
Mike Iselyd8554972006-06-26 20:58:46 -0300719 .def.type_enum.value_names = tab
720
Mike Isely33213962006-06-25 20:04:40 -0300721#define DEFBOOL \
722 .type = pvr2_ctl_bool
723
Mike Iselyd8554972006-06-26 20:58:46 -0300724#define DEFMASK(msk,tab) \
725 .type = pvr2_ctl_bitmask, \
726 .def.type_bitmask.valid_bits = msk, \
727 .def.type_bitmask.bit_names = tab
728
729#define DEFREF(vname) \
730 .set_value = ctrl_set_##vname, \
731 .get_value = ctrl_get_##vname, \
732 .is_dirty = ctrl_isdirty_##vname, \
733 .clear_dirty = ctrl_cleardirty_##vname
734
735
736#define VCREATE_FUNCS(vname) \
737static int ctrl_get_##vname(struct pvr2_ctrl *cptr,int *vp) \
738{*vp = cptr->hdw->vname##_val; return 0;} \
739static int ctrl_set_##vname(struct pvr2_ctrl *cptr,int m,int v) \
740{cptr->hdw->vname##_val = v; cptr->hdw->vname##_dirty = !0; return 0;} \
741static int ctrl_isdirty_##vname(struct pvr2_ctrl *cptr) \
742{return cptr->hdw->vname##_dirty != 0;} \
743static void ctrl_cleardirty_##vname(struct pvr2_ctrl *cptr) \
744{cptr->hdw->vname##_dirty = 0;}
745
746VCREATE_FUNCS(brightness)
747VCREATE_FUNCS(contrast)
748VCREATE_FUNCS(saturation)
749VCREATE_FUNCS(hue)
750VCREATE_FUNCS(volume)
751VCREATE_FUNCS(balance)
752VCREATE_FUNCS(bass)
753VCREATE_FUNCS(treble)
754VCREATE_FUNCS(mute)
Mike Iselyc05c0462006-06-25 20:04:25 -0300755VCREATE_FUNCS(audiomode)
756VCREATE_FUNCS(res_hor)
757VCREATE_FUNCS(res_ver)
Mike Iselyd8554972006-06-26 20:58:46 -0300758VCREATE_FUNCS(srate)
Mike Iselyd8554972006-06-26 20:58:46 -0300759
Mike Iselyd8554972006-06-26 20:58:46 -0300760/* Table definition of all controls which can be manipulated */
761static const struct pvr2_ctl_info control_defs[] = {
762 {
763 .v4l_id = V4L2_CID_BRIGHTNESS,
764 .desc = "Brightness",
765 .name = "brightness",
766 .default_value = 128,
767 DEFREF(brightness),
768 DEFINT(0,255),
769 },{
770 .v4l_id = V4L2_CID_CONTRAST,
771 .desc = "Contrast",
772 .name = "contrast",
773 .default_value = 68,
774 DEFREF(contrast),
775 DEFINT(0,127),
776 },{
777 .v4l_id = V4L2_CID_SATURATION,
778 .desc = "Saturation",
779 .name = "saturation",
780 .default_value = 64,
781 DEFREF(saturation),
782 DEFINT(0,127),
783 },{
784 .v4l_id = V4L2_CID_HUE,
785 .desc = "Hue",
786 .name = "hue",
787 .default_value = 0,
788 DEFREF(hue),
789 DEFINT(-128,127),
790 },{
791 .v4l_id = V4L2_CID_AUDIO_VOLUME,
792 .desc = "Volume",
793 .name = "volume",
Mike Isely139eecf2006-12-27 23:36:33 -0300794 .default_value = 62000,
Mike Iselyd8554972006-06-26 20:58:46 -0300795 DEFREF(volume),
796 DEFINT(0,65535),
797 },{
798 .v4l_id = V4L2_CID_AUDIO_BALANCE,
799 .desc = "Balance",
800 .name = "balance",
801 .default_value = 0,
802 DEFREF(balance),
803 DEFINT(-32768,32767),
804 },{
805 .v4l_id = V4L2_CID_AUDIO_BASS,
806 .desc = "Bass",
807 .name = "bass",
808 .default_value = 0,
809 DEFREF(bass),
810 DEFINT(-32768,32767),
811 },{
812 .v4l_id = V4L2_CID_AUDIO_TREBLE,
813 .desc = "Treble",
814 .name = "treble",
815 .default_value = 0,
816 DEFREF(treble),
817 DEFINT(-32768,32767),
818 },{
819 .v4l_id = V4L2_CID_AUDIO_MUTE,
820 .desc = "Mute",
821 .name = "mute",
822 .default_value = 0,
823 DEFREF(mute),
Mike Isely33213962006-06-25 20:04:40 -0300824 DEFBOOL,
Mike Iselyd8554972006-06-26 20:58:46 -0300825 },{
Mike Iselyc05c0462006-06-25 20:04:25 -0300826 .desc = "Video Source",
827 .name = "input",
828 .internal_id = PVR2_CID_INPUT,
829 .default_value = PVR2_CVAL_INPUT_TV,
Mike Isely29bf5b12008-04-22 14:45:37 -0300830 .check_value = ctrl_check_input,
Mike Iselyc05c0462006-06-25 20:04:25 -0300831 DEFREF(input),
832 DEFENUM(control_values_input),
833 },{
834 .desc = "Audio Mode",
835 .name = "audio_mode",
836 .internal_id = PVR2_CID_AUDIOMODE,
837 .default_value = V4L2_TUNER_MODE_STEREO,
838 DEFREF(audiomode),
839 DEFENUM(control_values_audiomode),
840 },{
841 .desc = "Horizontal capture resolution",
842 .name = "resolution_hor",
843 .internal_id = PVR2_CID_HRES,
844 .default_value = 720,
845 DEFREF(res_hor),
Mike Isely3ad9fc32006-09-02 22:37:52 -0300846 DEFINT(19,720),
Mike Iselyc05c0462006-06-25 20:04:25 -0300847 },{
848 .desc = "Vertical capture resolution",
849 .name = "resolution_ver",
850 .internal_id = PVR2_CID_VRES,
851 .default_value = 480,
852 DEFREF(res_ver),
Mike Isely3ad9fc32006-09-02 22:37:52 -0300853 DEFINT(17,576),
854 /* Hook in check for video standard and adjust maximum
855 depending on the standard. */
856 .get_max_value = ctrl_vres_max_get,
857 .get_min_value = ctrl_vres_min_get,
Mike Iselyc05c0462006-06-25 20:04:25 -0300858 },{
Mike Iselyb30d2442006-06-25 20:05:01 -0300859 .v4l_id = V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ,
Mike Isely434449f2006-08-08 09:10:06 -0300860 .default_value = V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000,
861 .desc = "Audio Sampling Frequency",
Mike Iselyd8554972006-06-26 20:58:46 -0300862 .name = "srate",
Mike Iselyd8554972006-06-26 20:58:46 -0300863 DEFREF(srate),
864 DEFENUM(control_values_srate),
865 },{
Mike Iselyd8554972006-06-26 20:58:46 -0300866 .desc = "Tuner Frequency (Hz)",
867 .name = "frequency",
868 .internal_id = PVR2_CID_FREQUENCY,
Mike Isely1bde0282006-12-27 23:30:13 -0300869 .default_value = 0,
Mike Iselyd8554972006-06-26 20:58:46 -0300870 .set_value = ctrl_freq_set,
871 .get_value = ctrl_freq_get,
872 .is_dirty = ctrl_freq_is_dirty,
873 .clear_dirty = ctrl_freq_clear_dirty,
Mike Isely644afdb2007-01-20 00:19:23 -0300874 DEFINT(0,0),
Pantelis Koukousoulas25d85272006-12-27 23:06:04 -0300875 /* Hook in check for input value (tv/radio) and adjust
876 max/min values accordingly */
877 .get_max_value = ctrl_freq_max_get,
878 .get_min_value = ctrl_freq_min_get,
Mike Iselyd8554972006-06-26 20:58:46 -0300879 },{
880 .desc = "Channel",
881 .name = "channel",
882 .set_value = ctrl_channel_set,
883 .get_value = ctrl_channel_get,
884 DEFINT(0,FREQTABLE_SIZE),
885 },{
886 .desc = "Channel Program Frequency",
887 .name = "freq_table_value",
888 .set_value = ctrl_channelfreq_set,
889 .get_value = ctrl_channelfreq_get,
Mike Isely644afdb2007-01-20 00:19:23 -0300890 DEFINT(0,0),
Mike Isely1bde0282006-12-27 23:30:13 -0300891 /* Hook in check for input value (tv/radio) and adjust
892 max/min values accordingly */
Mike Isely1bde0282006-12-27 23:30:13 -0300893 .get_max_value = ctrl_freq_max_get,
894 .get_min_value = ctrl_freq_min_get,
Mike Iselyd8554972006-06-26 20:58:46 -0300895 },{
896 .desc = "Channel Program ID",
897 .name = "freq_table_channel",
898 .set_value = ctrl_channelprog_set,
899 .get_value = ctrl_channelprog_get,
900 DEFINT(0,FREQTABLE_SIZE),
901 },{
Mike Iselyd8554972006-06-26 20:58:46 -0300902 .desc = "Streaming Enabled",
903 .name = "streaming_enabled",
904 .get_value = ctrl_streamingenabled_get,
Mike Isely33213962006-06-25 20:04:40 -0300905 DEFBOOL,
Mike Iselyd8554972006-06-26 20:58:46 -0300906 },{
907 .desc = "USB Speed",
908 .name = "usb_speed",
909 .get_value = ctrl_hsm_get,
910 DEFENUM(control_values_hsm),
911 },{
Mike Isely681c7392007-11-26 01:48:52 -0300912 .desc = "Master State",
913 .name = "master_state",
914 .get_value = ctrl_masterstate_get,
915 DEFENUM(pvr2_state_names),
916 },{
Mike Iselyd8554972006-06-26 20:58:46 -0300917 .desc = "Signal Present",
918 .name = "signal_present",
919 .get_value = ctrl_signal_get,
Mike Isely18103c572007-01-20 00:09:47 -0300920 DEFINT(0,65535),
921 },{
922 .desc = "Audio Modes Present",
923 .name = "audio_modes_present",
924 .get_value = ctrl_audio_modes_present_get,
925 /* For this type we "borrow" the V4L2_TUNER_MODE enum from
926 v4l. Nothing outside of this module cares about this,
927 but I reuse it in order to also reuse the
928 control_values_audiomode string table. */
929 DEFMASK(((1 << V4L2_TUNER_MODE_MONO)|
930 (1 << V4L2_TUNER_MODE_STEREO)|
931 (1 << V4L2_TUNER_MODE_LANG1)|
932 (1 << V4L2_TUNER_MODE_LANG2)),
933 control_values_audiomode),
Mike Iselyd8554972006-06-26 20:58:46 -0300934 },{
935 .desc = "Video Standards Available Mask",
936 .name = "video_standard_mask_available",
937 .internal_id = PVR2_CID_STDAVAIL,
938 .skip_init = !0,
939 .get_value = ctrl_stdavail_get,
940 .set_value = ctrl_stdavail_set,
941 .val_to_sym = ctrl_std_val_to_sym,
942 .sym_to_val = ctrl_std_sym_to_val,
943 .type = pvr2_ctl_bitmask,
944 },{
945 .desc = "Video Standards In Use Mask",
946 .name = "video_standard_mask_active",
947 .internal_id = PVR2_CID_STDCUR,
948 .skip_init = !0,
949 .get_value = ctrl_stdcur_get,
950 .set_value = ctrl_stdcur_set,
951 .is_dirty = ctrl_stdcur_is_dirty,
952 .clear_dirty = ctrl_stdcur_clear_dirty,
953 .val_to_sym = ctrl_std_val_to_sym,
954 .sym_to_val = ctrl_std_sym_to_val,
955 .type = pvr2_ctl_bitmask,
956 },{
Mike Iselyd8554972006-06-26 20:58:46 -0300957 .desc = "Video Standard Name",
958 .name = "video_standard",
959 .internal_id = PVR2_CID_STDENUM,
960 .skip_init = !0,
961 .get_value = ctrl_stdenumcur_get,
962 .set_value = ctrl_stdenumcur_set,
963 .is_dirty = ctrl_stdenumcur_is_dirty,
964 .clear_dirty = ctrl_stdenumcur_clear_dirty,
965 .type = pvr2_ctl_enum,
966 }
967};
968
Ahmed S. Darwisheca8ebf2007-01-20 00:35:03 -0300969#define CTRLDEF_COUNT ARRAY_SIZE(control_defs)
Mike Iselyd8554972006-06-26 20:58:46 -0300970
971
972const char *pvr2_config_get_name(enum pvr2_config cfg)
973{
974 switch (cfg) {
975 case pvr2_config_empty: return "empty";
976 case pvr2_config_mpeg: return "mpeg";
977 case pvr2_config_vbi: return "vbi";
Mike Isely16eb40d2006-12-30 18:27:32 -0300978 case pvr2_config_pcm: return "pcm";
979 case pvr2_config_rawvideo: return "raw video";
Mike Iselyd8554972006-06-26 20:58:46 -0300980 }
981 return "<unknown>";
982}
983
984
985struct usb_device *pvr2_hdw_get_dev(struct pvr2_hdw *hdw)
986{
987 return hdw->usb_dev;
988}
989
990
991unsigned long pvr2_hdw_get_sn(struct pvr2_hdw *hdw)
992{
993 return hdw->serial_number;
994}
995
Mike Isely31a18542007-04-08 01:11:47 -0300996
997const char *pvr2_hdw_get_bus_info(struct pvr2_hdw *hdw)
998{
999 return hdw->bus_info;
1000}
1001
1002
Mike Isely1bde0282006-12-27 23:30:13 -03001003unsigned long pvr2_hdw_get_cur_freq(struct pvr2_hdw *hdw)
1004{
1005 return hdw->freqSelector ? hdw->freqValTelevision : hdw->freqValRadio;
1006}
1007
1008/* Set the currently tuned frequency and account for all possible
1009 driver-core side effects of this action. */
Adrian Bunkf55a8712008-04-18 05:38:56 -03001010static void pvr2_hdw_set_cur_freq(struct pvr2_hdw *hdw,unsigned long val)
Mike Isely1bde0282006-12-27 23:30:13 -03001011{
Mike Isely7c74e572007-01-20 00:15:41 -03001012 if (hdw->input_val == PVR2_CVAL_INPUT_RADIO) {
Mike Isely1bde0282006-12-27 23:30:13 -03001013 if (hdw->freqSelector) {
1014 /* Swing over to radio frequency selection */
1015 hdw->freqSelector = 0;
1016 hdw->freqDirty = !0;
1017 }
Mike Isely1bde0282006-12-27 23:30:13 -03001018 if (hdw->freqValRadio != val) {
1019 hdw->freqValRadio = val;
1020 hdw->freqSlotRadio = 0;
Mike Isely7c74e572007-01-20 00:15:41 -03001021 hdw->freqDirty = !0;
Mike Isely1bde0282006-12-27 23:30:13 -03001022 }
Mike Isely7c74e572007-01-20 00:15:41 -03001023 } else {
Mike Isely1bde0282006-12-27 23:30:13 -03001024 if (!(hdw->freqSelector)) {
1025 /* Swing over to television frequency selection */
1026 hdw->freqSelector = 1;
1027 hdw->freqDirty = !0;
1028 }
Mike Isely1bde0282006-12-27 23:30:13 -03001029 if (hdw->freqValTelevision != val) {
1030 hdw->freqValTelevision = val;
1031 hdw->freqSlotTelevision = 0;
Mike Isely7c74e572007-01-20 00:15:41 -03001032 hdw->freqDirty = !0;
Mike Isely1bde0282006-12-27 23:30:13 -03001033 }
Mike Isely1bde0282006-12-27 23:30:13 -03001034 }
1035}
1036
Mike Iselyd8554972006-06-26 20:58:46 -03001037int pvr2_hdw_get_unit_number(struct pvr2_hdw *hdw)
1038{
1039 return hdw->unit_number;
1040}
1041
1042
1043/* Attempt to locate one of the given set of files. Messages are logged
1044 appropriate to what has been found. The return value will be 0 or
1045 greater on success (it will be the index of the file name found) and
1046 fw_entry will be filled in. Otherwise a negative error is returned on
1047 failure. If the return value is -ENOENT then no viable firmware file
1048 could be located. */
1049static int pvr2_locate_firmware(struct pvr2_hdw *hdw,
1050 const struct firmware **fw_entry,
1051 const char *fwtypename,
1052 unsigned int fwcount,
1053 const char *fwnames[])
1054{
1055 unsigned int idx;
1056 int ret = -EINVAL;
1057 for (idx = 0; idx < fwcount; idx++) {
1058 ret = request_firmware(fw_entry,
1059 fwnames[idx],
1060 &hdw->usb_dev->dev);
1061 if (!ret) {
1062 trace_firmware("Located %s firmware: %s;"
1063 " uploading...",
1064 fwtypename,
1065 fwnames[idx]);
1066 return idx;
1067 }
1068 if (ret == -ENOENT) continue;
1069 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1070 "request_firmware fatal error with code=%d",ret);
1071 return ret;
1072 }
1073 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1074 "***WARNING***"
1075 " Device %s firmware"
1076 " seems to be missing.",
1077 fwtypename);
1078 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1079 "Did you install the pvrusb2 firmware files"
1080 " in their proper location?");
1081 if (fwcount == 1) {
1082 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1083 "request_firmware unable to locate %s file %s",
1084 fwtypename,fwnames[0]);
1085 } else {
1086 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1087 "request_firmware unable to locate"
1088 " one of the following %s files:",
1089 fwtypename);
1090 for (idx = 0; idx < fwcount; idx++) {
1091 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1092 "request_firmware: Failed to find %s",
1093 fwnames[idx]);
1094 }
1095 }
1096 return ret;
1097}
1098
1099
1100/*
1101 * pvr2_upload_firmware1().
1102 *
1103 * Send the 8051 firmware to the device. After the upload, arrange for
1104 * device to re-enumerate.
1105 *
1106 * NOTE : the pointer to the firmware data given by request_firmware()
1107 * is not suitable for an usb transaction.
1108 *
1109 */
Adrian Bunk07e337e2006-06-30 11:30:20 -03001110static int pvr2_upload_firmware1(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03001111{
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001112 const struct firmware *fw_entry = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001113 void *fw_ptr;
1114 unsigned int pipe;
1115 int ret;
1116 u16 address;
Mike Isely1d643a32007-09-08 22:18:50 -03001117
Mike Isely989eb152007-11-26 01:53:12 -03001118 if (!hdw->hdw_desc->fx2_firmware.cnt) {
Mike Isely1d643a32007-09-08 22:18:50 -03001119 hdw->fw1_state = FW1_STATE_OK;
Mike Isely56dcbfa2007-11-26 02:00:51 -03001120 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1121 "Connected device type defines"
1122 " no firmware to upload; ignoring firmware");
1123 return -ENOTTY;
Mike Isely1d643a32007-09-08 22:18:50 -03001124 }
1125
Mike Iselyd8554972006-06-26 20:58:46 -03001126 hdw->fw1_state = FW1_STATE_FAILED; // default result
1127
1128 trace_firmware("pvr2_upload_firmware1");
1129
1130 ret = pvr2_locate_firmware(hdw,&fw_entry,"fx2 controller",
Mike Isely989eb152007-11-26 01:53:12 -03001131 hdw->hdw_desc->fx2_firmware.cnt,
1132 hdw->hdw_desc->fx2_firmware.lst);
Mike Iselyd8554972006-06-26 20:58:46 -03001133 if (ret < 0) {
1134 if (ret == -ENOENT) hdw->fw1_state = FW1_STATE_MISSING;
1135 return ret;
1136 }
1137
1138 usb_settoggle(hdw->usb_dev, 0 & 0xf, !(0 & USB_DIR_IN), 0);
1139 usb_clear_halt(hdw->usb_dev, usb_sndbulkpipe(hdw->usb_dev, 0 & 0x7f));
1140
1141 pipe = usb_sndctrlpipe(hdw->usb_dev, 0);
1142
1143 if (fw_entry->size != 0x2000){
1144 pvr2_trace(PVR2_TRACE_ERROR_LEGS,"wrong fx2 firmware size");
1145 release_firmware(fw_entry);
1146 return -ENOMEM;
1147 }
1148
1149 fw_ptr = kmalloc(0x800, GFP_KERNEL);
1150 if (fw_ptr == NULL){
1151 release_firmware(fw_entry);
1152 return -ENOMEM;
1153 }
1154
1155 /* We have to hold the CPU during firmware upload. */
1156 pvr2_hdw_cpureset_assert(hdw,1);
1157
1158 /* upload the firmware to address 0000-1fff in 2048 (=0x800) bytes
1159 chunk. */
1160
1161 ret = 0;
1162 for(address = 0; address < fw_entry->size; address += 0x800) {
1163 memcpy(fw_ptr, fw_entry->data + address, 0x800);
1164 ret += usb_control_msg(hdw->usb_dev, pipe, 0xa0, 0x40, address,
1165 0, fw_ptr, 0x800, HZ);
1166 }
1167
1168 trace_firmware("Upload done, releasing device's CPU");
1169
1170 /* Now release the CPU. It will disconnect and reconnect later. */
1171 pvr2_hdw_cpureset_assert(hdw,0);
1172
1173 kfree(fw_ptr);
1174 release_firmware(fw_entry);
1175
1176 trace_firmware("Upload done (%d bytes sent)",ret);
1177
1178 /* We should have written 8192 bytes */
1179 if (ret == 8192) {
1180 hdw->fw1_state = FW1_STATE_RELOAD;
1181 return 0;
1182 }
1183
1184 return -EIO;
1185}
1186
1187
1188/*
1189 * pvr2_upload_firmware2()
1190 *
1191 * This uploads encoder firmware on endpoint 2.
1192 *
1193 */
1194
1195int pvr2_upload_firmware2(struct pvr2_hdw *hdw)
1196{
Mike Iselya0fd1cb2006-06-30 11:35:28 -03001197 const struct firmware *fw_entry = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03001198 void *fw_ptr;
Mike Isely90060d32007-02-08 02:02:53 -03001199 unsigned int pipe, fw_len, fw_done, bcnt, icnt;
Mike Iselyd8554972006-06-26 20:58:46 -03001200 int actual_length;
1201 int ret = 0;
1202 int fwidx;
1203 static const char *fw_files[] = {
1204 CX2341X_FIRM_ENC_FILENAME,
1205 };
1206
Mike Isely989eb152007-11-26 01:53:12 -03001207 if (hdw->hdw_desc->flag_skip_cx23416_firmware) {
Mike Isely1d643a32007-09-08 22:18:50 -03001208 return 0;
1209 }
1210
Mike Iselyd8554972006-06-26 20:58:46 -03001211 trace_firmware("pvr2_upload_firmware2");
1212
1213 ret = pvr2_locate_firmware(hdw,&fw_entry,"encoder",
Ahmed S. Darwisheca8ebf2007-01-20 00:35:03 -03001214 ARRAY_SIZE(fw_files), fw_files);
Mike Iselyd8554972006-06-26 20:58:46 -03001215 if (ret < 0) return ret;
1216 fwidx = ret;
1217 ret = 0;
Mike Iselyb30d2442006-06-25 20:05:01 -03001218 /* Since we're about to completely reinitialize the encoder,
1219 invalidate our cached copy of its configuration state. Next
1220 time we configure the encoder, then we'll fully configure it. */
1221 hdw->enc_cur_valid = 0;
Mike Iselyd8554972006-06-26 20:58:46 -03001222
Mike Iselyd913d632008-04-06 04:04:35 -03001223 /* Encoder is about to be reset so note that as far as we're
1224 concerned now, the encoder has never been run. */
1225 del_timer_sync(&hdw->encoder_run_timer);
1226 if (hdw->state_encoder_runok) {
1227 hdw->state_encoder_runok = 0;
1228 trace_stbit("state_encoder_runok",hdw->state_encoder_runok);
1229 }
1230
Mike Iselyd8554972006-06-26 20:58:46 -03001231 /* First prepare firmware loading */
1232 ret |= pvr2_write_register(hdw, 0x0048, 0xffffffff); /*interrupt mask*/
1233 ret |= pvr2_hdw_gpio_chg_dir(hdw,0xffffffff,0x00000088); /*gpio dir*/
1234 ret |= pvr2_hdw_gpio_chg_out(hdw,0xffffffff,0x00000008); /*gpio output state*/
1235 ret |= pvr2_hdw_cmd_deep_reset(hdw);
1236 ret |= pvr2_write_register(hdw, 0xa064, 0x00000000); /*APU command*/
1237 ret |= pvr2_hdw_gpio_chg_dir(hdw,0xffffffff,0x00000408); /*gpio dir*/
1238 ret |= pvr2_hdw_gpio_chg_out(hdw,0xffffffff,0x00000008); /*gpio output state*/
1239 ret |= pvr2_write_register(hdw, 0x9058, 0xffffffed); /*VPU ctrl*/
1240 ret |= pvr2_write_register(hdw, 0x9054, 0xfffffffd); /*reset hw blocks*/
1241 ret |= pvr2_write_register(hdw, 0x07f8, 0x80000800); /*encoder SDRAM refresh*/
1242 ret |= pvr2_write_register(hdw, 0x07fc, 0x0000001a); /*encoder SDRAM pre-charge*/
1243 ret |= pvr2_write_register(hdw, 0x0700, 0x00000000); /*I2C clock*/
1244 ret |= pvr2_write_register(hdw, 0xaa00, 0x00000000); /*unknown*/
1245 ret |= pvr2_write_register(hdw, 0xaa04, 0x00057810); /*unknown*/
1246 ret |= pvr2_write_register(hdw, 0xaa10, 0x00148500); /*unknown*/
1247 ret |= pvr2_write_register(hdw, 0xaa18, 0x00840000); /*unknown*/
Mike Isely1c9d10d2008-03-28 05:38:54 -03001248 ret |= pvr2_issue_simple_cmd(hdw,FX2CMD_FWPOST1);
1249 ret |= pvr2_issue_simple_cmd(hdw,FX2CMD_MEMSEL | (1 << 8) | (0 << 16));
Mike Iselyd8554972006-06-26 20:58:46 -03001250
1251 if (ret) {
1252 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1253 "firmware2 upload prep failed, ret=%d",ret);
1254 release_firmware(fw_entry);
Mike Isely21684ba2008-04-21 03:49:33 -03001255 goto done;
Mike Iselyd8554972006-06-26 20:58:46 -03001256 }
1257
1258 /* Now send firmware */
1259
1260 fw_len = fw_entry->size;
1261
Mike Isely90060d32007-02-08 02:02:53 -03001262 if (fw_len % sizeof(u32)) {
Mike Iselyd8554972006-06-26 20:58:46 -03001263 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1264 "size of %s firmware"
Mike Isely48dc30a2007-03-03 10:13:05 -02001265 " must be a multiple of %zu bytes",
Mike Isely90060d32007-02-08 02:02:53 -03001266 fw_files[fwidx],sizeof(u32));
Mike Iselyd8554972006-06-26 20:58:46 -03001267 release_firmware(fw_entry);
Mike Isely21684ba2008-04-21 03:49:33 -03001268 ret = -EINVAL;
1269 goto done;
Mike Iselyd8554972006-06-26 20:58:46 -03001270 }
1271
1272 fw_ptr = kmalloc(FIRMWARE_CHUNK_SIZE, GFP_KERNEL);
1273 if (fw_ptr == NULL){
1274 release_firmware(fw_entry);
1275 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1276 "failed to allocate memory for firmware2 upload");
Mike Isely21684ba2008-04-21 03:49:33 -03001277 ret = -ENOMEM;
1278 goto done;
Mike Iselyd8554972006-06-26 20:58:46 -03001279 }
1280
1281 pipe = usb_sndbulkpipe(hdw->usb_dev, PVR2_FIRMWARE_ENDPOINT);
1282
Mike Isely90060d32007-02-08 02:02:53 -03001283 fw_done = 0;
1284 for (fw_done = 0; fw_done < fw_len;) {
1285 bcnt = fw_len - fw_done;
1286 if (bcnt > FIRMWARE_CHUNK_SIZE) bcnt = FIRMWARE_CHUNK_SIZE;
1287 memcpy(fw_ptr, fw_entry->data + fw_done, bcnt);
1288 /* Usbsnoop log shows that we must swap bytes... */
1289 for (icnt = 0; icnt < bcnt/4 ; icnt++)
1290 ((u32 *)fw_ptr)[icnt] =
1291 ___swab32(((u32 *)fw_ptr)[icnt]);
Mike Iselyd8554972006-06-26 20:58:46 -03001292
Mike Isely90060d32007-02-08 02:02:53 -03001293 ret |= usb_bulk_msg(hdw->usb_dev, pipe, fw_ptr,bcnt,
Mike Iselyd8554972006-06-26 20:58:46 -03001294 &actual_length, HZ);
Mike Isely90060d32007-02-08 02:02:53 -03001295 ret |= (actual_length != bcnt);
1296 if (ret) break;
1297 fw_done += bcnt;
Mike Iselyd8554972006-06-26 20:58:46 -03001298 }
1299
1300 trace_firmware("upload of %s : %i / %i ",
1301 fw_files[fwidx],fw_done,fw_len);
1302
1303 kfree(fw_ptr);
1304 release_firmware(fw_entry);
1305
1306 if (ret) {
1307 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1308 "firmware2 upload transfer failure");
Mike Isely21684ba2008-04-21 03:49:33 -03001309 goto done;
Mike Iselyd8554972006-06-26 20:58:46 -03001310 }
1311
1312 /* Finish upload */
1313
1314 ret |= pvr2_write_register(hdw, 0x9054, 0xffffffff); /*reset hw blocks*/
1315 ret |= pvr2_write_register(hdw, 0x9058, 0xffffffe8); /*VPU ctrl*/
Mike Isely1c9d10d2008-03-28 05:38:54 -03001316 ret |= pvr2_issue_simple_cmd(hdw,FX2CMD_MEMSEL | (1 << 8) | (0 << 16));
Mike Iselyd8554972006-06-26 20:58:46 -03001317
1318 if (ret) {
1319 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1320 "firmware2 upload post-proc failure");
Mike Iselyd8554972006-06-26 20:58:46 -03001321 }
Mike Isely21684ba2008-04-21 03:49:33 -03001322
1323 done:
Mike Isely1df59f02008-04-21 03:50:39 -03001324 if (hdw->hdw_desc->signal_routing_scheme ==
1325 PVR2_ROUTING_SCHEME_GOTVIEW) {
1326 /* Ensure that GPIO 11 is set to output for GOTVIEW
1327 hardware. */
1328 pvr2_hdw_gpio_chg_dir(hdw,(1 << 11),~0);
1329 }
Mike Iselyd8554972006-06-26 20:58:46 -03001330 return ret;
1331}
1332
1333
Mike Isely681c7392007-11-26 01:48:52 -03001334static const char *pvr2_get_state_name(unsigned int st)
Mike Iselyd8554972006-06-26 20:58:46 -03001335{
Mike Isely681c7392007-11-26 01:48:52 -03001336 if (st < ARRAY_SIZE(pvr2_state_names)) {
1337 return pvr2_state_names[st];
Mike Iselyd8554972006-06-26 20:58:46 -03001338 }
Mike Isely681c7392007-11-26 01:48:52 -03001339 return "???";
Mike Iselyd8554972006-06-26 20:58:46 -03001340}
1341
Mike Isely681c7392007-11-26 01:48:52 -03001342static int pvr2_decoder_enable(struct pvr2_hdw *hdw,int enablefl)
Mike Iselyd8554972006-06-26 20:58:46 -03001343{
Mike Isely681c7392007-11-26 01:48:52 -03001344 if (!hdw->decoder_ctrl) {
1345 if (!hdw->flag_decoder_missed) {
1346 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1347 "WARNING: No decoder present");
1348 hdw->flag_decoder_missed = !0;
1349 trace_stbit("flag_decoder_missed",
1350 hdw->flag_decoder_missed);
1351 }
1352 return -EIO;
Mike Iselyd8554972006-06-26 20:58:46 -03001353 }
Mike Isely681c7392007-11-26 01:48:52 -03001354 hdw->decoder_ctrl->enable(hdw->decoder_ctrl->ctxt,enablefl);
Mike Iselyd8554972006-06-26 20:58:46 -03001355 return 0;
1356}
1357
1358
Mike Isely681c7392007-11-26 01:48:52 -03001359void pvr2_hdw_set_decoder(struct pvr2_hdw *hdw,struct pvr2_decoder_ctrl *ptr)
1360{
1361 if (hdw->decoder_ctrl == ptr) return;
1362 hdw->decoder_ctrl = ptr;
1363 if (hdw->decoder_ctrl && hdw->flag_decoder_missed) {
1364 hdw->flag_decoder_missed = 0;
1365 trace_stbit("flag_decoder_missed",
1366 hdw->flag_decoder_missed);
1367 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1368 "Decoder has appeared");
1369 pvr2_hdw_state_sched(hdw);
1370 }
1371}
1372
1373
1374int pvr2_hdw_get_state(struct pvr2_hdw *hdw)
1375{
1376 return hdw->master_state;
1377}
1378
1379
1380static int pvr2_hdw_untrip_unlocked(struct pvr2_hdw *hdw)
1381{
1382 if (!hdw->flag_tripped) return 0;
1383 hdw->flag_tripped = 0;
1384 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1385 "Clearing driver error statuss");
1386 return !0;
1387}
1388
1389
1390int pvr2_hdw_untrip(struct pvr2_hdw *hdw)
1391{
1392 int fl;
1393 LOCK_TAKE(hdw->big_lock); do {
1394 fl = pvr2_hdw_untrip_unlocked(hdw);
1395 } while (0); LOCK_GIVE(hdw->big_lock);
1396 if (fl) pvr2_hdw_state_sched(hdw);
1397 return 0;
1398}
1399
1400
Mike Isely681c7392007-11-26 01:48:52 -03001401
1402
Mike Iselyd8554972006-06-26 20:58:46 -03001403int pvr2_hdw_get_streaming(struct pvr2_hdw *hdw)
1404{
Mike Isely681c7392007-11-26 01:48:52 -03001405 return hdw->state_pipeline_req != 0;
Mike Iselyd8554972006-06-26 20:58:46 -03001406}
1407
1408
1409int pvr2_hdw_set_streaming(struct pvr2_hdw *hdw,int enable_flag)
1410{
Mike Isely681c7392007-11-26 01:48:52 -03001411 int ret,st;
Mike Iselyd8554972006-06-26 20:58:46 -03001412 LOCK_TAKE(hdw->big_lock); do {
Mike Isely681c7392007-11-26 01:48:52 -03001413 pvr2_hdw_untrip_unlocked(hdw);
1414 if ((!enable_flag) != !(hdw->state_pipeline_req)) {
1415 hdw->state_pipeline_req = enable_flag != 0;
1416 pvr2_trace(PVR2_TRACE_START_STOP,
1417 "/*--TRACE_STREAM--*/ %s",
1418 enable_flag ? "enable" : "disable");
1419 }
1420 pvr2_hdw_state_sched(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03001421 } while (0); LOCK_GIVE(hdw->big_lock);
Mike Isely681c7392007-11-26 01:48:52 -03001422 if ((ret = pvr2_hdw_wait(hdw,0)) < 0) return ret;
1423 if (enable_flag) {
1424 while ((st = hdw->master_state) != PVR2_STATE_RUN) {
1425 if (st != PVR2_STATE_READY) return -EIO;
1426 if ((ret = pvr2_hdw_wait(hdw,st)) < 0) return ret;
1427 }
1428 }
Mike Iselyd8554972006-06-26 20:58:46 -03001429 return 0;
1430}
1431
1432
1433int pvr2_hdw_set_stream_type(struct pvr2_hdw *hdw,enum pvr2_config config)
1434{
Mike Isely681c7392007-11-26 01:48:52 -03001435 int fl;
Mike Iselyd8554972006-06-26 20:58:46 -03001436 LOCK_TAKE(hdw->big_lock);
Mike Isely681c7392007-11-26 01:48:52 -03001437 if ((fl = (hdw->desired_stream_type != config)) != 0) {
1438 hdw->desired_stream_type = config;
1439 hdw->state_pipeline_config = 0;
1440 trace_stbit("state_pipeline_config",
1441 hdw->state_pipeline_config);
1442 pvr2_hdw_state_sched(hdw);
1443 }
Mike Iselyd8554972006-06-26 20:58:46 -03001444 LOCK_GIVE(hdw->big_lock);
Mike Isely681c7392007-11-26 01:48:52 -03001445 if (fl) return 0;
1446 return pvr2_hdw_wait(hdw,0);
Mike Iselyd8554972006-06-26 20:58:46 -03001447}
1448
1449
1450static int get_default_tuner_type(struct pvr2_hdw *hdw)
1451{
1452 int unit_number = hdw->unit_number;
1453 int tp = -1;
1454 if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
1455 tp = tuner[unit_number];
1456 }
1457 if (tp < 0) return -EINVAL;
1458 hdw->tuner_type = tp;
Mike Iselyaaf78842007-11-26 02:04:11 -03001459 hdw->tuner_updated = !0;
Mike Iselyd8554972006-06-26 20:58:46 -03001460 return 0;
1461}
1462
1463
1464static v4l2_std_id get_default_standard(struct pvr2_hdw *hdw)
1465{
1466 int unit_number = hdw->unit_number;
1467 int tp = 0;
1468 if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
1469 tp = video_std[unit_number];
Mike Isely6a540252007-12-02 23:51:34 -03001470 if (tp) return tp;
Mike Iselyd8554972006-06-26 20:58:46 -03001471 }
Mike Isely6a540252007-12-02 23:51:34 -03001472 return 0;
Mike Iselyd8554972006-06-26 20:58:46 -03001473}
1474
1475
1476static unsigned int get_default_error_tolerance(struct pvr2_hdw *hdw)
1477{
1478 int unit_number = hdw->unit_number;
1479 int tp = 0;
1480 if ((unit_number >= 0) && (unit_number < PVR_NUM)) {
1481 tp = tolerance[unit_number];
1482 }
1483 return tp;
1484}
1485
1486
1487static int pvr2_hdw_check_firmware(struct pvr2_hdw *hdw)
1488{
1489 /* Try a harmless request to fetch the eeprom's address over
1490 endpoint 1. See what happens. Only the full FX2 image can
1491 respond to this. If this probe fails then likely the FX2
1492 firmware needs be loaded. */
1493 int result;
1494 LOCK_TAKE(hdw->ctl_lock); do {
Michael Krufky8d364362007-01-22 02:17:55 -03001495 hdw->cmd_buffer[0] = FX2CMD_GET_EEPROM_ADDR;
Mike Iselyd8554972006-06-26 20:58:46 -03001496 result = pvr2_send_request_ex(hdw,HZ*1,!0,
1497 hdw->cmd_buffer,1,
1498 hdw->cmd_buffer,1);
1499 if (result < 0) break;
1500 } while(0); LOCK_GIVE(hdw->ctl_lock);
1501 if (result) {
1502 pvr2_trace(PVR2_TRACE_INIT,
1503 "Probe of device endpoint 1 result status %d",
1504 result);
1505 } else {
1506 pvr2_trace(PVR2_TRACE_INIT,
1507 "Probe of device endpoint 1 succeeded");
1508 }
1509 return result == 0;
1510}
1511
Mike Isely9f66d4e2007-09-08 22:28:51 -03001512struct pvr2_std_hack {
1513 v4l2_std_id pat; /* Pattern to match */
1514 v4l2_std_id msk; /* Which bits we care about */
1515 v4l2_std_id std; /* What additional standards or default to set */
1516};
1517
1518/* This data structure labels specific combinations of standards from
1519 tveeprom that we'll try to recognize. If we recognize one, then assume
1520 a specified default standard to use. This is here because tveeprom only
1521 tells us about available standards not the intended default standard (if
1522 any) for the device in question. We guess the default based on what has
1523 been reported as available. Note that this is only for guessing a
1524 default - which can always be overridden explicitly - and if the user
1525 has otherwise named a default then that default will always be used in
1526 place of this table. */
Tobias Klauserebff0332008-04-22 14:45:45 -03001527static const struct pvr2_std_hack std_eeprom_maps[] = {
Mike Isely9f66d4e2007-09-08 22:28:51 -03001528 { /* PAL(B/G) */
1529 .pat = V4L2_STD_B|V4L2_STD_GH,
1530 .std = V4L2_STD_PAL_B|V4L2_STD_PAL_B1|V4L2_STD_PAL_G,
1531 },
1532 { /* NTSC(M) */
1533 .pat = V4L2_STD_MN,
1534 .std = V4L2_STD_NTSC_M,
1535 },
1536 { /* PAL(I) */
1537 .pat = V4L2_STD_PAL_I,
1538 .std = V4L2_STD_PAL_I,
1539 },
1540 { /* SECAM(L/L') */
1541 .pat = V4L2_STD_SECAM_L|V4L2_STD_SECAM_LC,
1542 .std = V4L2_STD_SECAM_L|V4L2_STD_SECAM_LC,
1543 },
1544 { /* PAL(D/D1/K) */
1545 .pat = V4L2_STD_DK,
Roel Kluinea2562d2007-12-02 23:04:57 -03001546 .std = V4L2_STD_PAL_D|V4L2_STD_PAL_D1|V4L2_STD_PAL_K,
Mike Isely9f66d4e2007-09-08 22:28:51 -03001547 },
1548};
1549
Mike Iselyd8554972006-06-26 20:58:46 -03001550static void pvr2_hdw_setup_std(struct pvr2_hdw *hdw)
1551{
1552 char buf[40];
1553 unsigned int bcnt;
Mike Isely3d290bd2007-12-03 01:47:12 -03001554 v4l2_std_id std1,std2,std3;
Mike Iselyd8554972006-06-26 20:58:46 -03001555
1556 std1 = get_default_standard(hdw);
Mike Isely3d290bd2007-12-03 01:47:12 -03001557 std3 = std1 ? 0 : hdw->hdw_desc->default_std_mask;
Mike Iselyd8554972006-06-26 20:58:46 -03001558
1559 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),hdw->std_mask_eeprom);
Mike Isely56585382007-09-08 22:32:12 -03001560 pvr2_trace(PVR2_TRACE_STD,
Mike Isely56dcbfa2007-11-26 02:00:51 -03001561 "Supported video standard(s) reported available"
1562 " in hardware: %.*s",
Mike Iselyd8554972006-06-26 20:58:46 -03001563 bcnt,buf);
1564
1565 hdw->std_mask_avail = hdw->std_mask_eeprom;
1566
Mike Isely3d290bd2007-12-03 01:47:12 -03001567 std2 = (std1|std3) & ~hdw->std_mask_avail;
Mike Iselyd8554972006-06-26 20:58:46 -03001568 if (std2) {
1569 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),std2);
Mike Isely56585382007-09-08 22:32:12 -03001570 pvr2_trace(PVR2_TRACE_STD,
Mike Iselyd8554972006-06-26 20:58:46 -03001571 "Expanding supported video standards"
1572 " to include: %.*s",
1573 bcnt,buf);
1574 hdw->std_mask_avail |= std2;
1575 }
1576
1577 pvr2_hdw_internal_set_std_avail(hdw);
1578
1579 if (std1) {
1580 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),std1);
Mike Isely56585382007-09-08 22:32:12 -03001581 pvr2_trace(PVR2_TRACE_STD,
Mike Iselyd8554972006-06-26 20:58:46 -03001582 "Initial video standard forced to %.*s",
1583 bcnt,buf);
1584 hdw->std_mask_cur = std1;
1585 hdw->std_dirty = !0;
1586 pvr2_hdw_internal_find_stdenum(hdw);
1587 return;
1588 }
Mike Isely3d290bd2007-12-03 01:47:12 -03001589 if (std3) {
1590 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),std3);
1591 pvr2_trace(PVR2_TRACE_STD,
1592 "Initial video standard"
1593 " (determined by device type): %.*s",bcnt,buf);
1594 hdw->std_mask_cur = std3;
1595 hdw->std_dirty = !0;
1596 pvr2_hdw_internal_find_stdenum(hdw);
1597 return;
1598 }
Mike Iselyd8554972006-06-26 20:58:46 -03001599
Mike Isely9f66d4e2007-09-08 22:28:51 -03001600 {
1601 unsigned int idx;
1602 for (idx = 0; idx < ARRAY_SIZE(std_eeprom_maps); idx++) {
1603 if (std_eeprom_maps[idx].msk ?
1604 ((std_eeprom_maps[idx].pat ^
1605 hdw->std_mask_eeprom) &
1606 std_eeprom_maps[idx].msk) :
1607 (std_eeprom_maps[idx].pat !=
1608 hdw->std_mask_eeprom)) continue;
1609 bcnt = pvr2_std_id_to_str(buf,sizeof(buf),
1610 std_eeprom_maps[idx].std);
Mike Isely56585382007-09-08 22:32:12 -03001611 pvr2_trace(PVR2_TRACE_STD,
Mike Isely9f66d4e2007-09-08 22:28:51 -03001612 "Initial video standard guessed as %.*s",
1613 bcnt,buf);
1614 hdw->std_mask_cur = std_eeprom_maps[idx].std;
1615 hdw->std_dirty = !0;
1616 pvr2_hdw_internal_find_stdenum(hdw);
1617 return;
1618 }
1619 }
1620
Mike Iselyd8554972006-06-26 20:58:46 -03001621 if (hdw->std_enum_cnt > 1) {
1622 // Autoselect the first listed standard
1623 hdw->std_enum_cur = 1;
1624 hdw->std_mask_cur = hdw->std_defs[hdw->std_enum_cur-1].id;
1625 hdw->std_dirty = !0;
Mike Isely56585382007-09-08 22:32:12 -03001626 pvr2_trace(PVR2_TRACE_STD,
Mike Iselyd8554972006-06-26 20:58:46 -03001627 "Initial video standard auto-selected to %s",
1628 hdw->std_defs[hdw->std_enum_cur-1].name);
1629 return;
1630 }
1631
Mike Isely0885ba12006-06-25 21:30:47 -03001632 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
Mike Iselyd8554972006-06-26 20:58:46 -03001633 "Unable to select a viable initial video standard");
1634}
1635
1636
1637static void pvr2_hdw_setup_low(struct pvr2_hdw *hdw)
1638{
1639 int ret;
1640 unsigned int idx;
1641 struct pvr2_ctrl *cptr;
1642 int reloadFl = 0;
Mike Isely989eb152007-11-26 01:53:12 -03001643 if (hdw->hdw_desc->fx2_firmware.cnt) {
Mike Isely1d643a32007-09-08 22:18:50 -03001644 if (!reloadFl) {
1645 reloadFl =
1646 (hdw->usb_intf->cur_altsetting->desc.bNumEndpoints
1647 == 0);
1648 if (reloadFl) {
1649 pvr2_trace(PVR2_TRACE_INIT,
1650 "USB endpoint config looks strange"
1651 "; possibly firmware needs to be"
1652 " loaded");
1653 }
1654 }
1655 if (!reloadFl) {
1656 reloadFl = !pvr2_hdw_check_firmware(hdw);
1657 if (reloadFl) {
1658 pvr2_trace(PVR2_TRACE_INIT,
1659 "Check for FX2 firmware failed"
1660 "; possibly firmware needs to be"
1661 " loaded");
1662 }
1663 }
Mike Iselyd8554972006-06-26 20:58:46 -03001664 if (reloadFl) {
Mike Isely1d643a32007-09-08 22:18:50 -03001665 if (pvr2_upload_firmware1(hdw) != 0) {
1666 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1667 "Failure uploading firmware1");
1668 }
1669 return;
Mike Iselyd8554972006-06-26 20:58:46 -03001670 }
1671 }
Mike Iselyd8554972006-06-26 20:58:46 -03001672 hdw->fw1_state = FW1_STATE_OK;
1673
1674 if (initusbreset) {
1675 pvr2_hdw_device_reset(hdw);
1676 }
1677 if (!pvr2_hdw_dev_ok(hdw)) return;
1678
Mike Isely989eb152007-11-26 01:53:12 -03001679 for (idx = 0; idx < hdw->hdw_desc->client_modules.cnt; idx++) {
1680 request_module(hdw->hdw_desc->client_modules.lst[idx]);
Mike Iselyd8554972006-06-26 20:58:46 -03001681 }
1682
Mike Isely989eb152007-11-26 01:53:12 -03001683 if (!hdw->hdw_desc->flag_no_powerup) {
Mike Isely1d643a32007-09-08 22:18:50 -03001684 pvr2_hdw_cmd_powerup(hdw);
1685 if (!pvr2_hdw_dev_ok(hdw)) return;
Mike Iselyd8554972006-06-26 20:58:46 -03001686 }
1687
1688 // This step MUST happen after the earlier powerup step.
1689 pvr2_i2c_core_init(hdw);
1690 if (!pvr2_hdw_dev_ok(hdw)) return;
1691
Mike Iselyc05c0462006-06-25 20:04:25 -03001692 for (idx = 0; idx < CTRLDEF_COUNT; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03001693 cptr = hdw->controls + idx;
1694 if (cptr->info->skip_init) continue;
1695 if (!cptr->info->set_value) continue;
1696 cptr->info->set_value(cptr,~0,cptr->info->default_value);
1697 }
1698
Mike Isely1bde0282006-12-27 23:30:13 -03001699 /* Set up special default values for the television and radio
1700 frequencies here. It's not really important what these defaults
1701 are, but I set them to something usable in the Chicago area just
1702 to make driver testing a little easier. */
1703
1704 /* US Broadcast channel 7 (175.25 MHz) */
1705 hdw->freqValTelevision = 175250000L;
1706 /* 104.3 MHz, a usable FM station for my area */
1707 hdw->freqValRadio = 104300000L;
1708
Mike Iselyd8554972006-06-26 20:58:46 -03001709 // Do not use pvr2_reset_ctl_endpoints() here. It is not
1710 // thread-safe against the normal pvr2_send_request() mechanism.
1711 // (We should make it thread safe).
1712
Mike Iselyaaf78842007-11-26 02:04:11 -03001713 if (hdw->hdw_desc->flag_has_hauppauge_rom) {
1714 ret = pvr2_hdw_get_eeprom_addr(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03001715 if (!pvr2_hdw_dev_ok(hdw)) return;
Mike Iselyaaf78842007-11-26 02:04:11 -03001716 if (ret < 0) {
1717 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
1718 "Unable to determine location of eeprom,"
1719 " skipping");
1720 } else {
1721 hdw->eeprom_addr = ret;
1722 pvr2_eeprom_analyze(hdw);
1723 if (!pvr2_hdw_dev_ok(hdw)) return;
1724 }
1725 } else {
1726 hdw->tuner_type = hdw->hdw_desc->default_tuner_type;
1727 hdw->tuner_updated = !0;
1728 hdw->std_mask_eeprom = V4L2_STD_ALL;
Mike Iselyd8554972006-06-26 20:58:46 -03001729 }
1730
1731 pvr2_hdw_setup_std(hdw);
1732
1733 if (!get_default_tuner_type(hdw)) {
1734 pvr2_trace(PVR2_TRACE_INIT,
1735 "pvr2_hdw_setup: Tuner type overridden to %d",
1736 hdw->tuner_type);
1737 }
1738
Mike Iselyd8554972006-06-26 20:58:46 -03001739 pvr2_i2c_core_check_stale(hdw);
1740 hdw->tuner_updated = 0;
1741
1742 if (!pvr2_hdw_dev_ok(hdw)) return;
1743
Mike Isely1df59f02008-04-21 03:50:39 -03001744 if (hdw->hdw_desc->signal_routing_scheme ==
1745 PVR2_ROUTING_SCHEME_GOTVIEW) {
1746 /* Ensure that GPIO 11 is set to output for GOTVIEW
1747 hardware. */
1748 pvr2_hdw_gpio_chg_dir(hdw,(1 << 11),~0);
1749 }
1750
Mike Isely681c7392007-11-26 01:48:52 -03001751 pvr2_hdw_commit_setup(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03001752
1753 hdw->vid_stream = pvr2_stream_create();
1754 if (!pvr2_hdw_dev_ok(hdw)) return;
1755 pvr2_trace(PVR2_TRACE_INIT,
1756 "pvr2_hdw_setup: video stream is %p",hdw->vid_stream);
1757 if (hdw->vid_stream) {
1758 idx = get_default_error_tolerance(hdw);
1759 if (idx) {
1760 pvr2_trace(PVR2_TRACE_INIT,
1761 "pvr2_hdw_setup: video stream %p"
1762 " setting tolerance %u",
1763 hdw->vid_stream,idx);
1764 }
1765 pvr2_stream_setup(hdw->vid_stream,hdw->usb_dev,
1766 PVR2_VID_ENDPOINT,idx);
1767 }
1768
1769 if (!pvr2_hdw_dev_ok(hdw)) return;
1770
Mike Iselyd8554972006-06-26 20:58:46 -03001771 hdw->flag_init_ok = !0;
Mike Isely681c7392007-11-26 01:48:52 -03001772
1773 pvr2_hdw_state_sched(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03001774}
1775
1776
Mike Isely681c7392007-11-26 01:48:52 -03001777/* Set up the structure and attempt to put the device into a usable state.
1778 This can be a time-consuming operation, which is why it is not done
1779 internally as part of the create() step. */
1780static void pvr2_hdw_setup(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03001781{
1782 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_setup(hdw=%p) begin",hdw);
Mike Isely681c7392007-11-26 01:48:52 -03001783 do {
Mike Iselyd8554972006-06-26 20:58:46 -03001784 pvr2_hdw_setup_low(hdw);
1785 pvr2_trace(PVR2_TRACE_INIT,
1786 "pvr2_hdw_setup(hdw=%p) done, ok=%d init_ok=%d",
Mike Isely681c7392007-11-26 01:48:52 -03001787 hdw,pvr2_hdw_dev_ok(hdw),hdw->flag_init_ok);
Mike Iselyd8554972006-06-26 20:58:46 -03001788 if (pvr2_hdw_dev_ok(hdw)) {
Mike Isely681c7392007-11-26 01:48:52 -03001789 if (hdw->flag_init_ok) {
Mike Iselyd8554972006-06-26 20:58:46 -03001790 pvr2_trace(
1791 PVR2_TRACE_INFO,
1792 "Device initialization"
1793 " completed successfully.");
1794 break;
1795 }
1796 if (hdw->fw1_state == FW1_STATE_RELOAD) {
1797 pvr2_trace(
1798 PVR2_TRACE_INFO,
1799 "Device microcontroller firmware"
1800 " (re)loaded; it should now reset"
1801 " and reconnect.");
1802 break;
1803 }
1804 pvr2_trace(
1805 PVR2_TRACE_ERROR_LEGS,
1806 "Device initialization was not successful.");
1807 if (hdw->fw1_state == FW1_STATE_MISSING) {
1808 pvr2_trace(
1809 PVR2_TRACE_ERROR_LEGS,
1810 "Giving up since device"
1811 " microcontroller firmware"
1812 " appears to be missing.");
1813 break;
1814 }
1815 }
1816 if (procreload) {
1817 pvr2_trace(
1818 PVR2_TRACE_ERROR_LEGS,
1819 "Attempting pvrusb2 recovery by reloading"
1820 " primary firmware.");
1821 pvr2_trace(
1822 PVR2_TRACE_ERROR_LEGS,
1823 "If this works, device should disconnect"
1824 " and reconnect in a sane state.");
1825 hdw->fw1_state = FW1_STATE_UNKNOWN;
1826 pvr2_upload_firmware1(hdw);
1827 } else {
1828 pvr2_trace(
1829 PVR2_TRACE_ERROR_LEGS,
1830 "***WARNING*** pvrusb2 device hardware"
1831 " appears to be jammed"
1832 " and I can't clear it.");
1833 pvr2_trace(
1834 PVR2_TRACE_ERROR_LEGS,
1835 "You might need to power cycle"
1836 " the pvrusb2 device"
1837 " in order to recover.");
1838 }
Mike Isely681c7392007-11-26 01:48:52 -03001839 } while (0);
Mike Iselyd8554972006-06-26 20:58:46 -03001840 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_setup(hdw=%p) end",hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03001841}
1842
1843
Mike Iselyc4a88282008-04-22 14:45:44 -03001844/* Perform second stage initialization. Set callback pointer first so that
1845 we can avoid a possible initialization race (if the kernel thread runs
1846 before the callback has been set). */
Mike Isely794b1602008-04-22 14:45:45 -03001847int pvr2_hdw_initialize(struct pvr2_hdw *hdw,
1848 void (*callback_func)(void *),
1849 void *callback_data)
Mike Iselyc4a88282008-04-22 14:45:44 -03001850{
1851 LOCK_TAKE(hdw->big_lock); do {
Mike Isely97f26ff2008-04-07 02:22:43 -03001852 if (hdw->flag_disconnected) {
1853 /* Handle a race here: If we're already
1854 disconnected by this point, then give up. If we
1855 get past this then we'll remain connected for
1856 the duration of initialization since the entire
1857 initialization sequence is now protected by the
1858 big_lock. */
1859 break;
1860 }
Mike Iselyc4a88282008-04-22 14:45:44 -03001861 hdw->state_data = callback_data;
1862 hdw->state_func = callback_func;
Mike Isely97f26ff2008-04-07 02:22:43 -03001863 pvr2_hdw_setup(hdw);
Mike Iselyc4a88282008-04-22 14:45:44 -03001864 } while (0); LOCK_GIVE(hdw->big_lock);
Mike Isely794b1602008-04-22 14:45:45 -03001865 return hdw->flag_init_ok;
Mike Iselyc4a88282008-04-22 14:45:44 -03001866}
1867
1868
1869/* Create, set up, and return a structure for interacting with the
1870 underlying hardware. */
Mike Iselyd8554972006-06-26 20:58:46 -03001871struct pvr2_hdw *pvr2_hdw_create(struct usb_interface *intf,
1872 const struct usb_device_id *devid)
1873{
Mike Isely7fb20fa2008-04-22 14:45:37 -03001874 unsigned int idx,cnt1,cnt2,m;
Mike Iselyd8554972006-06-26 20:58:46 -03001875 struct pvr2_hdw *hdw;
Mike Iselyd8554972006-06-26 20:58:46 -03001876 int valid_std_mask;
1877 struct pvr2_ctrl *cptr;
Mike Isely989eb152007-11-26 01:53:12 -03001878 const struct pvr2_device_desc *hdw_desc;
Mike Iselyd8554972006-06-26 20:58:46 -03001879 __u8 ifnum;
Mike Iselyb30d2442006-06-25 20:05:01 -03001880 struct v4l2_queryctrl qctrl;
1881 struct pvr2_ctl_info *ciptr;
Mike Iselyd8554972006-06-26 20:58:46 -03001882
Mike Iselyd130fa82007-12-08 17:20:06 -03001883 hdw_desc = (const struct pvr2_device_desc *)(devid->driver_info);
Mike Iselyd8554972006-06-26 20:58:46 -03001884
Mike Iselyca545f72007-01-20 00:37:11 -03001885 hdw = kzalloc(sizeof(*hdw),GFP_KERNEL);
Mike Iselyd8554972006-06-26 20:58:46 -03001886 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_create: hdw=%p, type \"%s\"",
Mike Isely989eb152007-11-26 01:53:12 -03001887 hdw,hdw_desc->description);
Mike Iselyd8554972006-06-26 20:58:46 -03001888 if (!hdw) goto fail;
Mike Isely681c7392007-11-26 01:48:52 -03001889
1890 init_timer(&hdw->quiescent_timer);
1891 hdw->quiescent_timer.data = (unsigned long)hdw;
1892 hdw->quiescent_timer.function = pvr2_hdw_quiescent_timeout;
1893
1894 init_timer(&hdw->encoder_wait_timer);
1895 hdw->encoder_wait_timer.data = (unsigned long)hdw;
1896 hdw->encoder_wait_timer.function = pvr2_hdw_encoder_wait_timeout;
1897
Mike Iselyd913d632008-04-06 04:04:35 -03001898 init_timer(&hdw->encoder_run_timer);
1899 hdw->encoder_run_timer.data = (unsigned long)hdw;
1900 hdw->encoder_run_timer.function = pvr2_hdw_encoder_run_timeout;
1901
Mike Isely681c7392007-11-26 01:48:52 -03001902 hdw->master_state = PVR2_STATE_DEAD;
1903
1904 init_waitqueue_head(&hdw->state_wait_data);
1905
Mike Isely18103c572007-01-20 00:09:47 -03001906 hdw->tuner_signal_stale = !0;
Mike Iselyb30d2442006-06-25 20:05:01 -03001907 cx2341x_fill_defaults(&hdw->enc_ctl_state);
Mike Iselyd8554972006-06-26 20:58:46 -03001908
Mike Isely7fb20fa2008-04-22 14:45:37 -03001909 /* Calculate which inputs are OK */
1910 m = 0;
1911 if (hdw_desc->flag_has_analogtuner) m |= 1 << PVR2_CVAL_INPUT_TV;
Mike Iselye8f5bac2008-04-22 14:45:40 -03001912 if (hdw_desc->digital_control_scheme != PVR2_DIGITAL_SCHEME_NONE) {
1913 m |= 1 << PVR2_CVAL_INPUT_DTV;
1914 }
Mike Isely7fb20fa2008-04-22 14:45:37 -03001915 if (hdw_desc->flag_has_svideo) m |= 1 << PVR2_CVAL_INPUT_SVIDEO;
1916 if (hdw_desc->flag_has_composite) m |= 1 << PVR2_CVAL_INPUT_COMPOSITE;
1917 if (hdw_desc->flag_has_fmradio) m |= 1 << PVR2_CVAL_INPUT_RADIO;
1918 hdw->input_avail_mask = m;
Mike Isely1cb03b72008-04-21 03:47:43 -03001919 hdw->input_allowed_mask = hdw->input_avail_mask;
Mike Isely7fb20fa2008-04-22 14:45:37 -03001920
Mike Isely62433e32008-04-22 14:45:40 -03001921 /* If not a hybrid device, pathway_state never changes. So
1922 initialize it here to what it should forever be. */
1923 if (!(hdw->input_avail_mask & (1 << PVR2_CVAL_INPUT_DTV))) {
1924 hdw->pathway_state = PVR2_PATHWAY_ANALOG;
1925 } else if (!(hdw->input_avail_mask & (1 << PVR2_CVAL_INPUT_TV))) {
1926 hdw->pathway_state = PVR2_PATHWAY_DIGITAL;
1927 }
1928
Mike Iselyc05c0462006-06-25 20:04:25 -03001929 hdw->control_cnt = CTRLDEF_COUNT;
Mike Iselyb30d2442006-06-25 20:05:01 -03001930 hdw->control_cnt += MPEGDEF_COUNT;
Mike Iselyca545f72007-01-20 00:37:11 -03001931 hdw->controls = kzalloc(sizeof(struct pvr2_ctrl) * hdw->control_cnt,
Mike Iselyd8554972006-06-26 20:58:46 -03001932 GFP_KERNEL);
1933 if (!hdw->controls) goto fail;
Mike Isely989eb152007-11-26 01:53:12 -03001934 hdw->hdw_desc = hdw_desc;
Mike Iselyc05c0462006-06-25 20:04:25 -03001935 for (idx = 0; idx < hdw->control_cnt; idx++) {
1936 cptr = hdw->controls + idx;
1937 cptr->hdw = hdw;
1938 }
Mike Iselyd8554972006-06-26 20:58:46 -03001939 for (idx = 0; idx < 32; idx++) {
1940 hdw->std_mask_ptrs[idx] = hdw->std_mask_names[idx];
1941 }
Mike Iselyc05c0462006-06-25 20:04:25 -03001942 for (idx = 0; idx < CTRLDEF_COUNT; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03001943 cptr = hdw->controls + idx;
Mike Iselyd8554972006-06-26 20:58:46 -03001944 cptr->info = control_defs+idx;
1945 }
Mike Iselydbc40a02008-04-22 14:45:39 -03001946
1947 /* Ensure that default input choice is a valid one. */
1948 m = hdw->input_avail_mask;
1949 if (m) for (idx = 0; idx < (sizeof(m) << 3); idx++) {
1950 if (!((1 << idx) & m)) continue;
1951 hdw->input_val = idx;
1952 break;
1953 }
1954
Mike Iselyb30d2442006-06-25 20:05:01 -03001955 /* Define and configure additional controls from cx2341x module. */
Mike Iselyca545f72007-01-20 00:37:11 -03001956 hdw->mpeg_ctrl_info = kzalloc(
Mike Iselyb30d2442006-06-25 20:05:01 -03001957 sizeof(*(hdw->mpeg_ctrl_info)) * MPEGDEF_COUNT, GFP_KERNEL);
1958 if (!hdw->mpeg_ctrl_info) goto fail;
Mike Iselyb30d2442006-06-25 20:05:01 -03001959 for (idx = 0; idx < MPEGDEF_COUNT; idx++) {
1960 cptr = hdw->controls + idx + CTRLDEF_COUNT;
1961 ciptr = &(hdw->mpeg_ctrl_info[idx].info);
1962 ciptr->desc = hdw->mpeg_ctrl_info[idx].desc;
1963 ciptr->name = mpeg_ids[idx].strid;
1964 ciptr->v4l_id = mpeg_ids[idx].id;
1965 ciptr->skip_init = !0;
1966 ciptr->get_value = ctrl_cx2341x_get;
1967 ciptr->get_v4lflags = ctrl_cx2341x_getv4lflags;
1968 ciptr->is_dirty = ctrl_cx2341x_is_dirty;
1969 if (!idx) ciptr->clear_dirty = ctrl_cx2341x_clear_dirty;
1970 qctrl.id = ciptr->v4l_id;
1971 cx2341x_ctrl_query(&hdw->enc_ctl_state,&qctrl);
1972 if (!(qctrl.flags & V4L2_CTRL_FLAG_READ_ONLY)) {
1973 ciptr->set_value = ctrl_cx2341x_set;
1974 }
1975 strncpy(hdw->mpeg_ctrl_info[idx].desc,qctrl.name,
1976 PVR2_CTLD_INFO_DESC_SIZE);
1977 hdw->mpeg_ctrl_info[idx].desc[PVR2_CTLD_INFO_DESC_SIZE-1] = 0;
1978 ciptr->default_value = qctrl.default_value;
1979 switch (qctrl.type) {
1980 default:
1981 case V4L2_CTRL_TYPE_INTEGER:
1982 ciptr->type = pvr2_ctl_int;
1983 ciptr->def.type_int.min_value = qctrl.minimum;
1984 ciptr->def.type_int.max_value = qctrl.maximum;
1985 break;
1986 case V4L2_CTRL_TYPE_BOOLEAN:
1987 ciptr->type = pvr2_ctl_bool;
1988 break;
1989 case V4L2_CTRL_TYPE_MENU:
1990 ciptr->type = pvr2_ctl_enum;
1991 ciptr->def.type_enum.value_names =
1992 cx2341x_ctrl_get_menu(ciptr->v4l_id);
1993 for (cnt1 = 0;
1994 ciptr->def.type_enum.value_names[cnt1] != NULL;
1995 cnt1++) { }
1996 ciptr->def.type_enum.count = cnt1;
1997 break;
1998 }
1999 cptr->info = ciptr;
2000 }
Mike Iselyd8554972006-06-26 20:58:46 -03002001
2002 // Initialize video standard enum dynamic control
2003 cptr = pvr2_hdw_get_ctrl_by_id(hdw,PVR2_CID_STDENUM);
2004 if (cptr) {
2005 memcpy(&hdw->std_info_enum,cptr->info,
2006 sizeof(hdw->std_info_enum));
2007 cptr->info = &hdw->std_info_enum;
2008
2009 }
2010 // Initialize control data regarding video standard masks
2011 valid_std_mask = pvr2_std_get_usable();
2012 for (idx = 0; idx < 32; idx++) {
2013 if (!(valid_std_mask & (1 << idx))) continue;
2014 cnt1 = pvr2_std_id_to_str(
2015 hdw->std_mask_names[idx],
2016 sizeof(hdw->std_mask_names[idx])-1,
2017 1 << idx);
2018 hdw->std_mask_names[idx][cnt1] = 0;
2019 }
2020 cptr = pvr2_hdw_get_ctrl_by_id(hdw,PVR2_CID_STDAVAIL);
2021 if (cptr) {
2022 memcpy(&hdw->std_info_avail,cptr->info,
2023 sizeof(hdw->std_info_avail));
2024 cptr->info = &hdw->std_info_avail;
2025 hdw->std_info_avail.def.type_bitmask.bit_names =
2026 hdw->std_mask_ptrs;
2027 hdw->std_info_avail.def.type_bitmask.valid_bits =
2028 valid_std_mask;
2029 }
2030 cptr = pvr2_hdw_get_ctrl_by_id(hdw,PVR2_CID_STDCUR);
2031 if (cptr) {
2032 memcpy(&hdw->std_info_cur,cptr->info,
2033 sizeof(hdw->std_info_cur));
2034 cptr->info = &hdw->std_info_cur;
2035 hdw->std_info_cur.def.type_bitmask.bit_names =
2036 hdw->std_mask_ptrs;
2037 hdw->std_info_avail.def.type_bitmask.valid_bits =
2038 valid_std_mask;
2039 }
2040
2041 hdw->eeprom_addr = -1;
2042 hdw->unit_number = -1;
Mike Isely80793842006-12-27 23:12:28 -03002043 hdw->v4l_minor_number_video = -1;
2044 hdw->v4l_minor_number_vbi = -1;
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002045 hdw->v4l_minor_number_radio = -1;
Mike Iselyd8554972006-06-26 20:58:46 -03002046 hdw->ctl_write_buffer = kmalloc(PVR2_CTL_BUFFSIZE,GFP_KERNEL);
2047 if (!hdw->ctl_write_buffer) goto fail;
2048 hdw->ctl_read_buffer = kmalloc(PVR2_CTL_BUFFSIZE,GFP_KERNEL);
2049 if (!hdw->ctl_read_buffer) goto fail;
2050 hdw->ctl_write_urb = usb_alloc_urb(0,GFP_KERNEL);
2051 if (!hdw->ctl_write_urb) goto fail;
2052 hdw->ctl_read_urb = usb_alloc_urb(0,GFP_KERNEL);
2053 if (!hdw->ctl_read_urb) goto fail;
2054
Matthias Kaehlcke8df0c872007-04-28 20:00:18 -03002055 mutex_lock(&pvr2_unit_mtx); do {
Mike Iselyd8554972006-06-26 20:58:46 -03002056 for (idx = 0; idx < PVR_NUM; idx++) {
2057 if (unit_pointers[idx]) continue;
2058 hdw->unit_number = idx;
2059 unit_pointers[idx] = hdw;
2060 break;
2061 }
Matthias Kaehlcke8df0c872007-04-28 20:00:18 -03002062 } while (0); mutex_unlock(&pvr2_unit_mtx);
Mike Iselyd8554972006-06-26 20:58:46 -03002063
2064 cnt1 = 0;
2065 cnt2 = scnprintf(hdw->name+cnt1,sizeof(hdw->name)-cnt1,"pvrusb2");
2066 cnt1 += cnt2;
2067 if (hdw->unit_number >= 0) {
2068 cnt2 = scnprintf(hdw->name+cnt1,sizeof(hdw->name)-cnt1,"_%c",
2069 ('a' + hdw->unit_number));
2070 cnt1 += cnt2;
2071 }
2072 if (cnt1 >= sizeof(hdw->name)) cnt1 = sizeof(hdw->name)-1;
2073 hdw->name[cnt1] = 0;
2074
Mike Isely681c7392007-11-26 01:48:52 -03002075 hdw->workqueue = create_singlethread_workqueue(hdw->name);
2076 INIT_WORK(&hdw->workpoll,pvr2_hdw_worker_poll);
2077 INIT_WORK(&hdw->worki2csync,pvr2_hdw_worker_i2c);
Mike Isely681c7392007-11-26 01:48:52 -03002078
Mike Iselyd8554972006-06-26 20:58:46 -03002079 pvr2_trace(PVR2_TRACE_INIT,"Driver unit number is %d, name is %s",
2080 hdw->unit_number,hdw->name);
2081
2082 hdw->tuner_type = -1;
2083 hdw->flag_ok = !0;
Mike Iselyd8554972006-06-26 20:58:46 -03002084
2085 hdw->usb_intf = intf;
2086 hdw->usb_dev = interface_to_usbdev(intf);
2087
Mike Isely31a18542007-04-08 01:11:47 -03002088 scnprintf(hdw->bus_info,sizeof(hdw->bus_info),
2089 "usb %s address %d",
2090 hdw->usb_dev->dev.bus_id,
2091 hdw->usb_dev->devnum);
2092
Mike Iselyd8554972006-06-26 20:58:46 -03002093 ifnum = hdw->usb_intf->cur_altsetting->desc.bInterfaceNumber;
2094 usb_set_interface(hdw->usb_dev,ifnum,0);
2095
2096 mutex_init(&hdw->ctl_lock_mutex);
2097 mutex_init(&hdw->big_lock_mutex);
2098
2099 return hdw;
2100 fail:
2101 if (hdw) {
Mike Isely681c7392007-11-26 01:48:52 -03002102 del_timer_sync(&hdw->quiescent_timer);
Mike Iselyd913d632008-04-06 04:04:35 -03002103 del_timer_sync(&hdw->encoder_run_timer);
Mike Isely681c7392007-11-26 01:48:52 -03002104 del_timer_sync(&hdw->encoder_wait_timer);
2105 if (hdw->workqueue) {
2106 flush_workqueue(hdw->workqueue);
2107 destroy_workqueue(hdw->workqueue);
2108 hdw->workqueue = NULL;
2109 }
Mariusz Kozlowski5e55d2c2006-11-08 15:34:31 +01002110 usb_free_urb(hdw->ctl_read_urb);
2111 usb_free_urb(hdw->ctl_write_urb);
Mariusz Kozlowski22071a42007-01-07 10:33:39 -03002112 kfree(hdw->ctl_read_buffer);
2113 kfree(hdw->ctl_write_buffer);
2114 kfree(hdw->controls);
2115 kfree(hdw->mpeg_ctrl_info);
Mike Isely681c7392007-11-26 01:48:52 -03002116 kfree(hdw->std_defs);
2117 kfree(hdw->std_enum_names);
Mike Iselyd8554972006-06-26 20:58:46 -03002118 kfree(hdw);
2119 }
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002120 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002121}
2122
2123
2124/* Remove _all_ associations between this driver and the underlying USB
2125 layer. */
Adrian Bunk07e337e2006-06-30 11:30:20 -03002126static void pvr2_hdw_remove_usb_stuff(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002127{
2128 if (hdw->flag_disconnected) return;
2129 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_remove_usb_stuff: hdw=%p",hdw);
2130 if (hdw->ctl_read_urb) {
2131 usb_kill_urb(hdw->ctl_read_urb);
2132 usb_free_urb(hdw->ctl_read_urb);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002133 hdw->ctl_read_urb = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002134 }
2135 if (hdw->ctl_write_urb) {
2136 usb_kill_urb(hdw->ctl_write_urb);
2137 usb_free_urb(hdw->ctl_write_urb);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002138 hdw->ctl_write_urb = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002139 }
2140 if (hdw->ctl_read_buffer) {
2141 kfree(hdw->ctl_read_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002142 hdw->ctl_read_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002143 }
2144 if (hdw->ctl_write_buffer) {
2145 kfree(hdw->ctl_write_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002146 hdw->ctl_write_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002147 }
Mike Iselyd8554972006-06-26 20:58:46 -03002148 hdw->flag_disconnected = !0;
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002149 hdw->usb_dev = NULL;
2150 hdw->usb_intf = NULL;
Mike Isely681c7392007-11-26 01:48:52 -03002151 pvr2_hdw_render_useless(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03002152}
2153
2154
2155/* Destroy hardware interaction structure */
2156void pvr2_hdw_destroy(struct pvr2_hdw *hdw)
2157{
Mike Isely401c27c2007-09-08 22:11:46 -03002158 if (!hdw) return;
Mike Iselyd8554972006-06-26 20:58:46 -03002159 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_destroy: hdw=%p",hdw);
Mike Isely681c7392007-11-26 01:48:52 -03002160 if (hdw->workqueue) {
2161 flush_workqueue(hdw->workqueue);
2162 destroy_workqueue(hdw->workqueue);
2163 hdw->workqueue = NULL;
2164 }
Mike Isely8f591002008-04-22 14:45:45 -03002165 del_timer_sync(&hdw->quiescent_timer);
Mike Iselyd913d632008-04-06 04:04:35 -03002166 del_timer_sync(&hdw->encoder_run_timer);
Mike Isely8f591002008-04-22 14:45:45 -03002167 del_timer_sync(&hdw->encoder_wait_timer);
Mike Iselyd8554972006-06-26 20:58:46 -03002168 if (hdw->fw_buffer) {
2169 kfree(hdw->fw_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002170 hdw->fw_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002171 }
2172 if (hdw->vid_stream) {
2173 pvr2_stream_destroy(hdw->vid_stream);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002174 hdw->vid_stream = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002175 }
Mike Iselyd8554972006-06-26 20:58:46 -03002176 if (hdw->decoder_ctrl) {
2177 hdw->decoder_ctrl->detach(hdw->decoder_ctrl->ctxt);
2178 }
2179 pvr2_i2c_core_done(hdw);
2180 pvr2_hdw_remove_usb_stuff(hdw);
Matthias Kaehlcke8df0c872007-04-28 20:00:18 -03002181 mutex_lock(&pvr2_unit_mtx); do {
Mike Iselyd8554972006-06-26 20:58:46 -03002182 if ((hdw->unit_number >= 0) &&
2183 (hdw->unit_number < PVR_NUM) &&
2184 (unit_pointers[hdw->unit_number] == hdw)) {
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002185 unit_pointers[hdw->unit_number] = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002186 }
Matthias Kaehlcke8df0c872007-04-28 20:00:18 -03002187 } while (0); mutex_unlock(&pvr2_unit_mtx);
Mariusz Kozlowski22071a42007-01-07 10:33:39 -03002188 kfree(hdw->controls);
2189 kfree(hdw->mpeg_ctrl_info);
2190 kfree(hdw->std_defs);
2191 kfree(hdw->std_enum_names);
Mike Iselyd8554972006-06-26 20:58:46 -03002192 kfree(hdw);
2193}
2194
2195
Mike Iselyd8554972006-06-26 20:58:46 -03002196int pvr2_hdw_dev_ok(struct pvr2_hdw *hdw)
2197{
2198 return (hdw && hdw->flag_ok);
2199}
2200
2201
2202/* Called when hardware has been unplugged */
2203void pvr2_hdw_disconnect(struct pvr2_hdw *hdw)
2204{
2205 pvr2_trace(PVR2_TRACE_INIT,"pvr2_hdw_disconnect(hdw=%p)",hdw);
2206 LOCK_TAKE(hdw->big_lock);
2207 LOCK_TAKE(hdw->ctl_lock);
2208 pvr2_hdw_remove_usb_stuff(hdw);
2209 LOCK_GIVE(hdw->ctl_lock);
2210 LOCK_GIVE(hdw->big_lock);
2211}
2212
2213
2214// Attempt to autoselect an appropriate value for std_enum_cur given
2215// whatever is currently in std_mask_cur
Adrian Bunk07e337e2006-06-30 11:30:20 -03002216static void pvr2_hdw_internal_find_stdenum(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002217{
2218 unsigned int idx;
2219 for (idx = 1; idx < hdw->std_enum_cnt; idx++) {
2220 if (hdw->std_defs[idx-1].id == hdw->std_mask_cur) {
2221 hdw->std_enum_cur = idx;
2222 return;
2223 }
2224 }
2225 hdw->std_enum_cur = 0;
2226}
2227
2228
2229// Calculate correct set of enumerated standards based on currently known
2230// set of available standards bits.
Adrian Bunk07e337e2006-06-30 11:30:20 -03002231static void pvr2_hdw_internal_set_std_avail(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002232{
2233 struct v4l2_standard *newstd;
2234 unsigned int std_cnt;
2235 unsigned int idx;
2236
2237 newstd = pvr2_std_create_enum(&std_cnt,hdw->std_mask_avail);
2238
2239 if (hdw->std_defs) {
2240 kfree(hdw->std_defs);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002241 hdw->std_defs = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002242 }
2243 hdw->std_enum_cnt = 0;
2244 if (hdw->std_enum_names) {
2245 kfree(hdw->std_enum_names);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002246 hdw->std_enum_names = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002247 }
2248
2249 if (!std_cnt) {
2250 pvr2_trace(
2251 PVR2_TRACE_ERROR_LEGS,
2252 "WARNING: Failed to identify any viable standards");
2253 }
2254 hdw->std_enum_names = kmalloc(sizeof(char *)*(std_cnt+1),GFP_KERNEL);
2255 hdw->std_enum_names[0] = "none";
2256 for (idx = 0; idx < std_cnt; idx++) {
2257 hdw->std_enum_names[idx+1] =
2258 newstd[idx].name;
2259 }
2260 // Set up the dynamic control for this standard
2261 hdw->std_info_enum.def.type_enum.value_names = hdw->std_enum_names;
2262 hdw->std_info_enum.def.type_enum.count = std_cnt+1;
2263 hdw->std_defs = newstd;
2264 hdw->std_enum_cnt = std_cnt+1;
2265 hdw->std_enum_cur = 0;
2266 hdw->std_info_cur.def.type_bitmask.valid_bits = hdw->std_mask_avail;
2267}
2268
2269
2270int pvr2_hdw_get_stdenum_value(struct pvr2_hdw *hdw,
2271 struct v4l2_standard *std,
2272 unsigned int idx)
2273{
2274 int ret = -EINVAL;
2275 if (!idx) return ret;
2276 LOCK_TAKE(hdw->big_lock); do {
2277 if (idx >= hdw->std_enum_cnt) break;
2278 idx--;
2279 memcpy(std,hdw->std_defs+idx,sizeof(*std));
2280 ret = 0;
2281 } while (0); LOCK_GIVE(hdw->big_lock);
2282 return ret;
2283}
2284
2285
2286/* Get the number of defined controls */
2287unsigned int pvr2_hdw_get_ctrl_count(struct pvr2_hdw *hdw)
2288{
Mike Iselyc05c0462006-06-25 20:04:25 -03002289 return hdw->control_cnt;
Mike Iselyd8554972006-06-26 20:58:46 -03002290}
2291
2292
2293/* Retrieve a control handle given its index (0..count-1) */
2294struct pvr2_ctrl *pvr2_hdw_get_ctrl_by_index(struct pvr2_hdw *hdw,
2295 unsigned int idx)
2296{
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002297 if (idx >= hdw->control_cnt) return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002298 return hdw->controls + idx;
2299}
2300
2301
2302/* Retrieve a control handle given its index (0..count-1) */
2303struct pvr2_ctrl *pvr2_hdw_get_ctrl_by_id(struct pvr2_hdw *hdw,
2304 unsigned int ctl_id)
2305{
2306 struct pvr2_ctrl *cptr;
2307 unsigned int idx;
2308 int i;
2309
2310 /* This could be made a lot more efficient, but for now... */
Mike Iselyc05c0462006-06-25 20:04:25 -03002311 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002312 cptr = hdw->controls + idx;
2313 i = cptr->info->internal_id;
2314 if (i && (i == ctl_id)) return cptr;
2315 }
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002316 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002317}
2318
2319
Mike Iselya761f432006-06-25 20:04:44 -03002320/* Given a V4L ID, retrieve the control structure associated with it. */
Mike Iselyd8554972006-06-26 20:58:46 -03002321struct pvr2_ctrl *pvr2_hdw_get_ctrl_v4l(struct pvr2_hdw *hdw,unsigned int ctl_id)
2322{
2323 struct pvr2_ctrl *cptr;
2324 unsigned int idx;
2325 int i;
2326
2327 /* This could be made a lot more efficient, but for now... */
Mike Iselyc05c0462006-06-25 20:04:25 -03002328 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002329 cptr = hdw->controls + idx;
2330 i = cptr->info->v4l_id;
2331 if (i && (i == ctl_id)) return cptr;
2332 }
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002333 return NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002334}
2335
2336
Mike Iselya761f432006-06-25 20:04:44 -03002337/* Given a V4L ID for its immediate predecessor, retrieve the control
2338 structure associated with it. */
2339struct pvr2_ctrl *pvr2_hdw_get_ctrl_nextv4l(struct pvr2_hdw *hdw,
2340 unsigned int ctl_id)
2341{
2342 struct pvr2_ctrl *cptr,*cp2;
2343 unsigned int idx;
2344 int i;
2345
2346 /* This could be made a lot more efficient, but for now... */
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002347 cp2 = NULL;
Mike Iselya761f432006-06-25 20:04:44 -03002348 for (idx = 0; idx < hdw->control_cnt; idx++) {
2349 cptr = hdw->controls + idx;
2350 i = cptr->info->v4l_id;
2351 if (!i) continue;
2352 if (i <= ctl_id) continue;
2353 if (cp2 && (cp2->info->v4l_id < i)) continue;
2354 cp2 = cptr;
2355 }
2356 return cp2;
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002357 return NULL;
Mike Iselya761f432006-06-25 20:04:44 -03002358}
2359
2360
Mike Iselyd8554972006-06-26 20:58:46 -03002361static const char *get_ctrl_typename(enum pvr2_ctl_type tp)
2362{
2363 switch (tp) {
2364 case pvr2_ctl_int: return "integer";
2365 case pvr2_ctl_enum: return "enum";
Mike Isely33213962006-06-25 20:04:40 -03002366 case pvr2_ctl_bool: return "boolean";
Mike Iselyd8554972006-06-26 20:58:46 -03002367 case pvr2_ctl_bitmask: return "bitmask";
2368 }
2369 return "";
2370}
2371
2372
Mike Isely681c7392007-11-26 01:48:52 -03002373/* Figure out if we need to commit control changes. If so, mark internal
2374 state flags to indicate this fact and return true. Otherwise do nothing
2375 else and return false. */
2376static int pvr2_hdw_commit_setup(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002377{
Mike Iselyd8554972006-06-26 20:58:46 -03002378 unsigned int idx;
2379 struct pvr2_ctrl *cptr;
2380 int value;
2381 int commit_flag = 0;
2382 char buf[100];
2383 unsigned int bcnt,ccnt;
2384
Mike Iselyc05c0462006-06-25 20:04:25 -03002385 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002386 cptr = hdw->controls + idx;
Al Viro5fa12472008-03-29 03:07:38 +00002387 if (!cptr->info->is_dirty) continue;
Mike Iselyd8554972006-06-26 20:58:46 -03002388 if (!cptr->info->is_dirty(cptr)) continue;
Mike Iselyfe23a282007-01-20 00:10:55 -03002389 commit_flag = !0;
Mike Iselyd8554972006-06-26 20:58:46 -03002390
Mike Iselyfe23a282007-01-20 00:10:55 -03002391 if (!(pvrusb2_debug & PVR2_TRACE_CTL)) continue;
Mike Iselyd8554972006-06-26 20:58:46 -03002392 bcnt = scnprintf(buf,sizeof(buf),"\"%s\" <-- ",
2393 cptr->info->name);
2394 value = 0;
2395 cptr->info->get_value(cptr,&value);
2396 pvr2_ctrl_value_to_sym_internal(cptr,~0,value,
2397 buf+bcnt,
2398 sizeof(buf)-bcnt,&ccnt);
2399 bcnt += ccnt;
2400 bcnt += scnprintf(buf+bcnt,sizeof(buf)-bcnt," <%s>",
2401 get_ctrl_typename(cptr->info->type));
2402 pvr2_trace(PVR2_TRACE_CTL,
2403 "/*--TRACE_COMMIT--*/ %.*s",
2404 bcnt,buf);
2405 }
2406
2407 if (!commit_flag) {
2408 /* Nothing has changed */
2409 return 0;
2410 }
2411
Mike Isely681c7392007-11-26 01:48:52 -03002412 hdw->state_pipeline_config = 0;
2413 trace_stbit("state_pipeline_config",hdw->state_pipeline_config);
2414 pvr2_hdw_state_sched(hdw);
2415
2416 return !0;
2417}
2418
2419
2420/* Perform all operations needed to commit all control changes. This must
2421 be performed in synchronization with the pipeline state and is thus
2422 expected to be called as part of the driver's worker thread. Return
2423 true if commit successful, otherwise return false to indicate that
2424 commit isn't possible at this time. */
2425static int pvr2_hdw_commit_execute(struct pvr2_hdw *hdw)
2426{
2427 unsigned int idx;
2428 struct pvr2_ctrl *cptr;
2429 int disruptive_change;
2430
Mike Iselyd8554972006-06-26 20:58:46 -03002431 /* When video standard changes, reset the hres and vres values -
2432 but if the user has pending changes there, then let the changes
2433 take priority. */
2434 if (hdw->std_dirty) {
2435 /* Rewrite the vertical resolution to be appropriate to the
2436 video standard that has been selected. */
2437 int nvres;
2438 if (hdw->std_mask_cur & V4L2_STD_525_60) {
2439 nvres = 480;
2440 } else {
2441 nvres = 576;
2442 }
2443 if (nvres != hdw->res_ver_val) {
2444 hdw->res_ver_val = nvres;
2445 hdw->res_ver_dirty = !0;
2446 }
Mike Iselyd8554972006-06-26 20:58:46 -03002447 }
2448
Mike Isely38d9a2c2008-03-28 05:30:48 -03002449 if (hdw->input_dirty && hdw->state_pathway_ok &&
Mike Isely62433e32008-04-22 14:45:40 -03002450 (((hdw->input_val == PVR2_CVAL_INPUT_DTV) ?
2451 PVR2_PATHWAY_DIGITAL : PVR2_PATHWAY_ANALOG) !=
2452 hdw->pathway_state)) {
2453 /* Change of mode being asked for... */
2454 hdw->state_pathway_ok = 0;
Mike Iselye9db1ff2008-04-22 14:45:41 -03002455 trace_stbit("state_pathway_ok",hdw->state_pathway_ok);
Mike Isely62433e32008-04-22 14:45:40 -03002456 }
2457 if (!hdw->state_pathway_ok) {
2458 /* Can't commit anything until pathway is ok. */
2459 return 0;
2460 }
Mike Isely681c7392007-11-26 01:48:52 -03002461 /* If any of the below has changed, then we can't do the update
2462 while the pipeline is running. Pipeline must be paused first
2463 and decoder -> encoder connection be made quiescent before we
2464 can proceed. */
2465 disruptive_change =
2466 (hdw->std_dirty ||
2467 hdw->enc_unsafe_stale ||
2468 hdw->srate_dirty ||
2469 hdw->res_ver_dirty ||
2470 hdw->res_hor_dirty ||
2471 hdw->input_dirty ||
2472 (hdw->active_stream_type != hdw->desired_stream_type));
2473 if (disruptive_change && !hdw->state_pipeline_idle) {
2474 /* Pipeline is not idle; we can't proceed. Arrange to
2475 cause pipeline to stop so that we can try this again
2476 later.... */
2477 hdw->state_pipeline_pause = !0;
2478 return 0;
Mike Iselyd8554972006-06-26 20:58:46 -03002479 }
2480
Mike Iselyb30d2442006-06-25 20:05:01 -03002481 if (hdw->srate_dirty) {
2482 /* Write new sample rate into control structure since
2483 * the master copy is stale. We must track srate
2484 * separate from the mpeg control structure because
2485 * other logic also uses this value. */
2486 struct v4l2_ext_controls cs;
2487 struct v4l2_ext_control c1;
2488 memset(&cs,0,sizeof(cs));
2489 memset(&c1,0,sizeof(c1));
2490 cs.controls = &c1;
2491 cs.count = 1;
2492 c1.id = V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ;
2493 c1.value = hdw->srate_val;
Hans Verkuil01f1e442007-08-21 18:32:42 -03002494 cx2341x_ext_ctrls(&hdw->enc_ctl_state, 0, &cs,VIDIOC_S_EXT_CTRLS);
Mike Iselyb30d2442006-06-25 20:05:01 -03002495 }
Mike Iselyc05c0462006-06-25 20:04:25 -03002496
Mike Iselyd8554972006-06-26 20:58:46 -03002497 /* Scan i2c core at this point - before we clear all the dirty
2498 bits. Various parts of the i2c core will notice dirty bits as
2499 appropriate and arrange to broadcast or directly send updates to
2500 the client drivers in order to keep everything in sync */
2501 pvr2_i2c_core_check_stale(hdw);
2502
Mike Iselyc05c0462006-06-25 20:04:25 -03002503 for (idx = 0; idx < hdw->control_cnt; idx++) {
Mike Iselyd8554972006-06-26 20:58:46 -03002504 cptr = hdw->controls + idx;
2505 if (!cptr->info->clear_dirty) continue;
2506 cptr->info->clear_dirty(cptr);
2507 }
2508
Mike Isely681c7392007-11-26 01:48:52 -03002509 if (hdw->active_stream_type != hdw->desired_stream_type) {
2510 /* Handle any side effects of stream config here */
2511 hdw->active_stream_type = hdw->desired_stream_type;
2512 }
2513
Mike Isely1df59f02008-04-21 03:50:39 -03002514 if (hdw->hdw_desc->signal_routing_scheme ==
2515 PVR2_ROUTING_SCHEME_GOTVIEW) {
2516 u32 b;
2517 /* Handle GOTVIEW audio switching */
2518 pvr2_hdw_gpio_get_out(hdw,&b);
2519 if (hdw->input_val == PVR2_CVAL_INPUT_RADIO) {
2520 /* Set GPIO 11 */
2521 pvr2_hdw_gpio_chg_out(hdw,(1 << 11),~0);
2522 } else {
2523 /* Clear GPIO 11 */
2524 pvr2_hdw_gpio_chg_out(hdw,(1 << 11),0);
2525 }
2526 }
2527
Mike Iselyd8554972006-06-26 20:58:46 -03002528 /* Now execute i2c core update */
2529 pvr2_i2c_core_sync(hdw);
2530
Mike Isely62433e32008-04-22 14:45:40 -03002531 if ((hdw->pathway_state == PVR2_PATHWAY_ANALOG) &&
2532 hdw->state_encoder_run) {
2533 /* If encoder isn't running or it can't be touched, then
2534 this will get worked out later when we start the
2535 encoder. */
Mike Isely681c7392007-11-26 01:48:52 -03002536 if (pvr2_encoder_adjust(hdw) < 0) return !0;
2537 }
Mike Iselyd8554972006-06-26 20:58:46 -03002538
Mike Isely681c7392007-11-26 01:48:52 -03002539 hdw->state_pipeline_config = !0;
2540 trace_stbit("state_pipeline_config",hdw->state_pipeline_config);
2541 return !0;
Mike Iselyd8554972006-06-26 20:58:46 -03002542}
2543
2544
2545int pvr2_hdw_commit_ctl(struct pvr2_hdw *hdw)
2546{
Mike Isely681c7392007-11-26 01:48:52 -03002547 int fl;
2548 LOCK_TAKE(hdw->big_lock);
2549 fl = pvr2_hdw_commit_setup(hdw);
2550 LOCK_GIVE(hdw->big_lock);
2551 if (!fl) return 0;
2552 return pvr2_hdw_wait(hdw,0);
Mike Iselyd8554972006-06-26 20:58:46 -03002553}
2554
2555
Mike Isely681c7392007-11-26 01:48:52 -03002556static void pvr2_hdw_worker_i2c(struct work_struct *work)
Mike Iselyd8554972006-06-26 20:58:46 -03002557{
Mike Isely681c7392007-11-26 01:48:52 -03002558 struct pvr2_hdw *hdw = container_of(work,struct pvr2_hdw,worki2csync);
Mike Iselyd8554972006-06-26 20:58:46 -03002559 LOCK_TAKE(hdw->big_lock); do {
2560 pvr2_i2c_core_sync(hdw);
2561 } while (0); LOCK_GIVE(hdw->big_lock);
2562}
2563
2564
Mike Isely681c7392007-11-26 01:48:52 -03002565static void pvr2_hdw_worker_poll(struct work_struct *work)
Mike Iselyd8554972006-06-26 20:58:46 -03002566{
Mike Isely681c7392007-11-26 01:48:52 -03002567 int fl = 0;
2568 struct pvr2_hdw *hdw = container_of(work,struct pvr2_hdw,workpoll);
Mike Iselyd8554972006-06-26 20:58:46 -03002569 LOCK_TAKE(hdw->big_lock); do {
Mike Isely681c7392007-11-26 01:48:52 -03002570 fl = pvr2_hdw_state_eval(hdw);
2571 } while (0); LOCK_GIVE(hdw->big_lock);
2572 if (fl && hdw->state_func) {
2573 hdw->state_func(hdw->state_data);
2574 }
2575}
2576
2577
Mike Isely681c7392007-11-26 01:48:52 -03002578static int pvr2_hdw_wait(struct pvr2_hdw *hdw,int state)
Mike Iselyd8554972006-06-26 20:58:46 -03002579{
Mike Isely681c7392007-11-26 01:48:52 -03002580 return wait_event_interruptible(
2581 hdw->state_wait_data,
2582 (hdw->state_stale == 0) &&
2583 (!state || (hdw->master_state != state)));
Mike Iselyd8554972006-06-26 20:58:46 -03002584}
2585
Mike Isely681c7392007-11-26 01:48:52 -03002586
Mike Iselyd8554972006-06-26 20:58:46 -03002587/* Return name for this driver instance */
2588const char *pvr2_hdw_get_driver_name(struct pvr2_hdw *hdw)
2589{
2590 return hdw->name;
2591}
2592
2593
Mike Isely78a47102007-11-26 01:58:20 -03002594const char *pvr2_hdw_get_desc(struct pvr2_hdw *hdw)
2595{
2596 return hdw->hdw_desc->description;
2597}
2598
2599
2600const char *pvr2_hdw_get_type(struct pvr2_hdw *hdw)
2601{
2602 return hdw->hdw_desc->shortname;
2603}
2604
2605
Mike Iselyd8554972006-06-26 20:58:46 -03002606int pvr2_hdw_is_hsm(struct pvr2_hdw *hdw)
2607{
2608 int result;
2609 LOCK_TAKE(hdw->ctl_lock); do {
Michael Krufky8d364362007-01-22 02:17:55 -03002610 hdw->cmd_buffer[0] = FX2CMD_GET_USB_SPEED;
Mike Iselyd8554972006-06-26 20:58:46 -03002611 result = pvr2_send_request(hdw,
2612 hdw->cmd_buffer,1,
2613 hdw->cmd_buffer,1);
2614 if (result < 0) break;
2615 result = (hdw->cmd_buffer[0] != 0);
2616 } while(0); LOCK_GIVE(hdw->ctl_lock);
2617 return result;
2618}
2619
2620
Mike Isely18103c572007-01-20 00:09:47 -03002621/* Execute poll of tuner status */
2622void pvr2_hdw_execute_tuner_poll(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03002623{
Mike Iselyd8554972006-06-26 20:58:46 -03002624 LOCK_TAKE(hdw->big_lock); do {
Mike Isely18103c572007-01-20 00:09:47 -03002625 pvr2_i2c_core_status_poll(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03002626 } while (0); LOCK_GIVE(hdw->big_lock);
Mike Isely18103c572007-01-20 00:09:47 -03002627}
2628
2629
2630/* Return information about the tuner */
2631int pvr2_hdw_get_tuner_status(struct pvr2_hdw *hdw,struct v4l2_tuner *vtp)
2632{
2633 LOCK_TAKE(hdw->big_lock); do {
2634 if (hdw->tuner_signal_stale) {
2635 pvr2_i2c_core_status_poll(hdw);
2636 }
2637 memcpy(vtp,&hdw->tuner_signal_info,sizeof(struct v4l2_tuner));
2638 } while (0); LOCK_GIVE(hdw->big_lock);
2639 return 0;
Mike Iselyd8554972006-06-26 20:58:46 -03002640}
2641
2642
2643/* Get handle to video output stream */
2644struct pvr2_stream *pvr2_hdw_get_video_stream(struct pvr2_hdw *hp)
2645{
2646 return hp->vid_stream;
2647}
2648
2649
2650void pvr2_hdw_trigger_module_log(struct pvr2_hdw *hdw)
2651{
Mike Isely4f1a3e52006-06-25 20:04:31 -03002652 int nr = pvr2_hdw_get_unit_number(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03002653 LOCK_TAKE(hdw->big_lock); do {
2654 hdw->log_requested = !0;
Mike Isely4f1a3e52006-06-25 20:04:31 -03002655 printk(KERN_INFO "pvrusb2: ================= START STATUS CARD #%d =================\n", nr);
Mike Iselyd8554972006-06-26 20:58:46 -03002656 pvr2_i2c_core_check_stale(hdw);
2657 hdw->log_requested = 0;
2658 pvr2_i2c_core_sync(hdw);
Mike Iselyb30d2442006-06-25 20:05:01 -03002659 pvr2_trace(PVR2_TRACE_INFO,"cx2341x config:");
Hans Verkuil99eb44f2006-06-26 18:24:05 -03002660 cx2341x_log_status(&hdw->enc_ctl_state, "pvrusb2");
Mike Isely681c7392007-11-26 01:48:52 -03002661 pvr2_hdw_state_log_state(hdw);
Mike Isely4f1a3e52006-06-25 20:04:31 -03002662 printk(KERN_INFO "pvrusb2: ================== END STATUS CARD #%d ==================\n", nr);
Mike Iselyd8554972006-06-26 20:58:46 -03002663 } while (0); LOCK_GIVE(hdw->big_lock);
2664}
2665
Mike Isely4db666c2007-09-08 22:16:27 -03002666
2667/* Grab EEPROM contents, needed for direct method. */
2668#define EEPROM_SIZE 8192
2669#define trace_eeprom(...) pvr2_trace(PVR2_TRACE_EEPROM,__VA_ARGS__)
2670static u8 *pvr2_full_eeprom_fetch(struct pvr2_hdw *hdw)
2671{
2672 struct i2c_msg msg[2];
2673 u8 *eeprom;
2674 u8 iadd[2];
2675 u8 addr;
2676 u16 eepromSize;
2677 unsigned int offs;
2678 int ret;
2679 int mode16 = 0;
2680 unsigned pcnt,tcnt;
2681 eeprom = kmalloc(EEPROM_SIZE,GFP_KERNEL);
2682 if (!eeprom) {
2683 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2684 "Failed to allocate memory"
2685 " required to read eeprom");
2686 return NULL;
2687 }
2688
2689 trace_eeprom("Value for eeprom addr from controller was 0x%x",
2690 hdw->eeprom_addr);
2691 addr = hdw->eeprom_addr;
2692 /* Seems that if the high bit is set, then the *real* eeprom
2693 address is shifted right now bit position (noticed this in
2694 newer PVR USB2 hardware) */
2695 if (addr & 0x80) addr >>= 1;
2696
2697 /* FX2 documentation states that a 16bit-addressed eeprom is
2698 expected if the I2C address is an odd number (yeah, this is
2699 strange but it's what they do) */
2700 mode16 = (addr & 1);
2701 eepromSize = (mode16 ? EEPROM_SIZE : 256);
2702 trace_eeprom("Examining %d byte eeprom at location 0x%x"
2703 " using %d bit addressing",eepromSize,addr,
2704 mode16 ? 16 : 8);
2705
2706 msg[0].addr = addr;
2707 msg[0].flags = 0;
2708 msg[0].len = mode16 ? 2 : 1;
2709 msg[0].buf = iadd;
2710 msg[1].addr = addr;
2711 msg[1].flags = I2C_M_RD;
2712
2713 /* We have to do the actual eeprom data fetch ourselves, because
2714 (1) we're only fetching part of the eeprom, and (2) if we were
2715 getting the whole thing our I2C driver can't grab it in one
2716 pass - which is what tveeprom is otherwise going to attempt */
2717 memset(eeprom,0,EEPROM_SIZE);
2718 for (tcnt = 0; tcnt < EEPROM_SIZE; tcnt += pcnt) {
2719 pcnt = 16;
2720 if (pcnt + tcnt > EEPROM_SIZE) pcnt = EEPROM_SIZE-tcnt;
2721 offs = tcnt + (eepromSize - EEPROM_SIZE);
2722 if (mode16) {
2723 iadd[0] = offs >> 8;
2724 iadd[1] = offs;
2725 } else {
2726 iadd[0] = offs;
2727 }
2728 msg[1].len = pcnt;
2729 msg[1].buf = eeprom+tcnt;
2730 if ((ret = i2c_transfer(&hdw->i2c_adap,
2731 msg,ARRAY_SIZE(msg))) != 2) {
2732 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2733 "eeprom fetch set offs err=%d",ret);
2734 kfree(eeprom);
2735 return NULL;
2736 }
2737 }
2738 return eeprom;
2739}
2740
2741
2742void pvr2_hdw_cpufw_set_enabled(struct pvr2_hdw *hdw,
2743 int prom_flag,
2744 int enable_flag)
Mike Iselyd8554972006-06-26 20:58:46 -03002745{
2746 int ret;
2747 u16 address;
2748 unsigned int pipe;
2749 LOCK_TAKE(hdw->big_lock); do {
Al Viro5fa12472008-03-29 03:07:38 +00002750 if ((hdw->fw_buffer == NULL) == !enable_flag) break;
Mike Iselyd8554972006-06-26 20:58:46 -03002751
2752 if (!enable_flag) {
2753 pvr2_trace(PVR2_TRACE_FIRMWARE,
2754 "Cleaning up after CPU firmware fetch");
2755 kfree(hdw->fw_buffer);
Mike Iselya0fd1cb2006-06-30 11:35:28 -03002756 hdw->fw_buffer = NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002757 hdw->fw_size = 0;
Mike Isely4db666c2007-09-08 22:16:27 -03002758 if (hdw->fw_cpu_flag) {
2759 /* Now release the CPU. It will disconnect
2760 and reconnect later. */
2761 pvr2_hdw_cpureset_assert(hdw,0);
2762 }
Mike Iselyd8554972006-06-26 20:58:46 -03002763 break;
2764 }
2765
Mike Isely4db666c2007-09-08 22:16:27 -03002766 hdw->fw_cpu_flag = (prom_flag == 0);
2767 if (hdw->fw_cpu_flag) {
2768 pvr2_trace(PVR2_TRACE_FIRMWARE,
2769 "Preparing to suck out CPU firmware");
2770 hdw->fw_size = 0x2000;
2771 hdw->fw_buffer = kzalloc(hdw->fw_size,GFP_KERNEL);
2772 if (!hdw->fw_buffer) {
2773 hdw->fw_size = 0;
2774 break;
2775 }
2776
2777 /* We have to hold the CPU during firmware upload. */
2778 pvr2_hdw_cpureset_assert(hdw,1);
2779
2780 /* download the firmware from address 0000-1fff in 2048
2781 (=0x800) bytes chunk. */
2782
2783 pvr2_trace(PVR2_TRACE_FIRMWARE,
2784 "Grabbing CPU firmware");
2785 pipe = usb_rcvctrlpipe(hdw->usb_dev, 0);
2786 for(address = 0; address < hdw->fw_size;
2787 address += 0x800) {
2788 ret = usb_control_msg(hdw->usb_dev,pipe,
2789 0xa0,0xc0,
2790 address,0,
2791 hdw->fw_buffer+address,
2792 0x800,HZ);
2793 if (ret < 0) break;
2794 }
2795
2796 pvr2_trace(PVR2_TRACE_FIRMWARE,
2797 "Done grabbing CPU firmware");
2798 } else {
2799 pvr2_trace(PVR2_TRACE_FIRMWARE,
2800 "Sucking down EEPROM contents");
2801 hdw->fw_buffer = pvr2_full_eeprom_fetch(hdw);
2802 if (!hdw->fw_buffer) {
2803 pvr2_trace(PVR2_TRACE_FIRMWARE,
2804 "EEPROM content suck failed.");
2805 break;
2806 }
2807 hdw->fw_size = EEPROM_SIZE;
2808 pvr2_trace(PVR2_TRACE_FIRMWARE,
2809 "Done sucking down EEPROM contents");
Mike Iselyd8554972006-06-26 20:58:46 -03002810 }
2811
Mike Iselyd8554972006-06-26 20:58:46 -03002812 } while (0); LOCK_GIVE(hdw->big_lock);
2813}
2814
2815
2816/* Return true if we're in a mode for retrieval CPU firmware */
2817int pvr2_hdw_cpufw_get_enabled(struct pvr2_hdw *hdw)
2818{
Al Viro5fa12472008-03-29 03:07:38 +00002819 return hdw->fw_buffer != NULL;
Mike Iselyd8554972006-06-26 20:58:46 -03002820}
2821
2822
2823int pvr2_hdw_cpufw_get(struct pvr2_hdw *hdw,unsigned int offs,
2824 char *buf,unsigned int cnt)
2825{
2826 int ret = -EINVAL;
2827 LOCK_TAKE(hdw->big_lock); do {
2828 if (!buf) break;
2829 if (!cnt) break;
2830
2831 if (!hdw->fw_buffer) {
2832 ret = -EIO;
2833 break;
2834 }
2835
2836 if (offs >= hdw->fw_size) {
2837 pvr2_trace(PVR2_TRACE_FIRMWARE,
2838 "Read firmware data offs=%d EOF",
2839 offs);
2840 ret = 0;
2841 break;
2842 }
2843
2844 if (offs + cnt > hdw->fw_size) cnt = hdw->fw_size - offs;
2845
2846 memcpy(buf,hdw->fw_buffer+offs,cnt);
2847
2848 pvr2_trace(PVR2_TRACE_FIRMWARE,
2849 "Read firmware data offs=%d cnt=%d",
2850 offs,cnt);
2851 ret = cnt;
2852 } while (0); LOCK_GIVE(hdw->big_lock);
2853
2854 return ret;
2855}
2856
2857
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002858int pvr2_hdw_v4l_get_minor_number(struct pvr2_hdw *hdw,
Mike Isely80793842006-12-27 23:12:28 -03002859 enum pvr2_v4l_type index)
Mike Iselyd8554972006-06-26 20:58:46 -03002860{
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002861 switch (index) {
Mike Isely80793842006-12-27 23:12:28 -03002862 case pvr2_v4l_type_video: return hdw->v4l_minor_number_video;
2863 case pvr2_v4l_type_vbi: return hdw->v4l_minor_number_vbi;
2864 case pvr2_v4l_type_radio: return hdw->v4l_minor_number_radio;
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002865 default: return -1;
2866 }
Mike Iselyd8554972006-06-26 20:58:46 -03002867}
2868
2869
Pantelis Koukousoulas2fdf3d92006-12-27 23:07:58 -03002870/* Store a v4l minor device number */
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002871void pvr2_hdw_v4l_store_minor_number(struct pvr2_hdw *hdw,
Mike Isely80793842006-12-27 23:12:28 -03002872 enum pvr2_v4l_type index,int v)
Mike Iselyd8554972006-06-26 20:58:46 -03002873{
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002874 switch (index) {
Mike Isely80793842006-12-27 23:12:28 -03002875 case pvr2_v4l_type_video: hdw->v4l_minor_number_video = v;
2876 case pvr2_v4l_type_vbi: hdw->v4l_minor_number_vbi = v;
2877 case pvr2_v4l_type_radio: hdw->v4l_minor_number_radio = v;
Mike Iselyfd5a75f2006-12-27 23:11:22 -03002878 default: break;
2879 }
Mike Iselyd8554972006-06-26 20:58:46 -03002880}
2881
2882
David Howells7d12e782006-10-05 14:55:46 +01002883static void pvr2_ctl_write_complete(struct urb *urb)
Mike Iselyd8554972006-06-26 20:58:46 -03002884{
2885 struct pvr2_hdw *hdw = urb->context;
2886 hdw->ctl_write_pend_flag = 0;
2887 if (hdw->ctl_read_pend_flag) return;
2888 complete(&hdw->ctl_done);
2889}
2890
2891
David Howells7d12e782006-10-05 14:55:46 +01002892static void pvr2_ctl_read_complete(struct urb *urb)
Mike Iselyd8554972006-06-26 20:58:46 -03002893{
2894 struct pvr2_hdw *hdw = urb->context;
2895 hdw->ctl_read_pend_flag = 0;
2896 if (hdw->ctl_write_pend_flag) return;
2897 complete(&hdw->ctl_done);
2898}
2899
2900
2901static void pvr2_ctl_timeout(unsigned long data)
2902{
2903 struct pvr2_hdw *hdw = (struct pvr2_hdw *)data;
2904 if (hdw->ctl_write_pend_flag || hdw->ctl_read_pend_flag) {
2905 hdw->ctl_timeout_flag = !0;
Mariusz Kozlowski5e55d2c2006-11-08 15:34:31 +01002906 if (hdw->ctl_write_pend_flag)
Mike Iselyd8554972006-06-26 20:58:46 -03002907 usb_unlink_urb(hdw->ctl_write_urb);
Mariusz Kozlowski5e55d2c2006-11-08 15:34:31 +01002908 if (hdw->ctl_read_pend_flag)
Mike Iselyd8554972006-06-26 20:58:46 -03002909 usb_unlink_urb(hdw->ctl_read_urb);
Mike Iselyd8554972006-06-26 20:58:46 -03002910 }
2911}
2912
2913
Mike Iselye61b6fc2006-07-18 22:42:18 -03002914/* Issue a command and get a response from the device. This extended
2915 version includes a probe flag (which if set means that device errors
2916 should not be logged or treated as fatal) and a timeout in jiffies.
2917 This can be used to non-lethally probe the health of endpoint 1. */
Adrian Bunk07e337e2006-06-30 11:30:20 -03002918static int pvr2_send_request_ex(struct pvr2_hdw *hdw,
2919 unsigned int timeout,int probe_fl,
2920 void *write_data,unsigned int write_len,
2921 void *read_data,unsigned int read_len)
Mike Iselyd8554972006-06-26 20:58:46 -03002922{
2923 unsigned int idx;
2924 int status = 0;
2925 struct timer_list timer;
2926 if (!hdw->ctl_lock_held) {
2927 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2928 "Attempted to execute control transfer"
2929 " without lock!!");
2930 return -EDEADLK;
2931 }
Mike Isely681c7392007-11-26 01:48:52 -03002932 if (!hdw->flag_ok && !probe_fl) {
Mike Iselyd8554972006-06-26 20:58:46 -03002933 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2934 "Attempted to execute control transfer"
2935 " when device not ok");
2936 return -EIO;
2937 }
2938 if (!(hdw->ctl_read_urb && hdw->ctl_write_urb)) {
2939 if (!probe_fl) {
2940 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
2941 "Attempted to execute control transfer"
2942 " when USB is disconnected");
2943 }
2944 return -ENOTTY;
2945 }
2946
2947 /* Ensure that we have sane parameters */
2948 if (!write_data) write_len = 0;
2949 if (!read_data) read_len = 0;
2950 if (write_len > PVR2_CTL_BUFFSIZE) {
2951 pvr2_trace(
2952 PVR2_TRACE_ERROR_LEGS,
2953 "Attempted to execute %d byte"
2954 " control-write transfer (limit=%d)",
2955 write_len,PVR2_CTL_BUFFSIZE);
2956 return -EINVAL;
2957 }
2958 if (read_len > PVR2_CTL_BUFFSIZE) {
2959 pvr2_trace(
2960 PVR2_TRACE_ERROR_LEGS,
2961 "Attempted to execute %d byte"
2962 " control-read transfer (limit=%d)",
2963 write_len,PVR2_CTL_BUFFSIZE);
2964 return -EINVAL;
2965 }
2966 if ((!write_len) && (!read_len)) {
2967 pvr2_trace(
2968 PVR2_TRACE_ERROR_LEGS,
2969 "Attempted to execute null control transfer?");
2970 return -EINVAL;
2971 }
2972
2973
2974 hdw->cmd_debug_state = 1;
2975 if (write_len) {
2976 hdw->cmd_debug_code = ((unsigned char *)write_data)[0];
2977 } else {
2978 hdw->cmd_debug_code = 0;
2979 }
2980 hdw->cmd_debug_write_len = write_len;
2981 hdw->cmd_debug_read_len = read_len;
2982
2983 /* Initialize common stuff */
2984 init_completion(&hdw->ctl_done);
2985 hdw->ctl_timeout_flag = 0;
2986 hdw->ctl_write_pend_flag = 0;
2987 hdw->ctl_read_pend_flag = 0;
2988 init_timer(&timer);
2989 timer.expires = jiffies + timeout;
2990 timer.data = (unsigned long)hdw;
2991 timer.function = pvr2_ctl_timeout;
2992
2993 if (write_len) {
2994 hdw->cmd_debug_state = 2;
2995 /* Transfer write data to internal buffer */
2996 for (idx = 0; idx < write_len; idx++) {
2997 hdw->ctl_write_buffer[idx] =
2998 ((unsigned char *)write_data)[idx];
2999 }
3000 /* Initiate a write request */
3001 usb_fill_bulk_urb(hdw->ctl_write_urb,
3002 hdw->usb_dev,
3003 usb_sndbulkpipe(hdw->usb_dev,
3004 PVR2_CTL_WRITE_ENDPOINT),
3005 hdw->ctl_write_buffer,
3006 write_len,
3007 pvr2_ctl_write_complete,
3008 hdw);
3009 hdw->ctl_write_urb->actual_length = 0;
3010 hdw->ctl_write_pend_flag = !0;
3011 status = usb_submit_urb(hdw->ctl_write_urb,GFP_KERNEL);
3012 if (status < 0) {
3013 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3014 "Failed to submit write-control"
3015 " URB status=%d",status);
3016 hdw->ctl_write_pend_flag = 0;
3017 goto done;
3018 }
3019 }
3020
3021 if (read_len) {
3022 hdw->cmd_debug_state = 3;
3023 memset(hdw->ctl_read_buffer,0x43,read_len);
3024 /* Initiate a read request */
3025 usb_fill_bulk_urb(hdw->ctl_read_urb,
3026 hdw->usb_dev,
3027 usb_rcvbulkpipe(hdw->usb_dev,
3028 PVR2_CTL_READ_ENDPOINT),
3029 hdw->ctl_read_buffer,
3030 read_len,
3031 pvr2_ctl_read_complete,
3032 hdw);
3033 hdw->ctl_read_urb->actual_length = 0;
3034 hdw->ctl_read_pend_flag = !0;
3035 status = usb_submit_urb(hdw->ctl_read_urb,GFP_KERNEL);
3036 if (status < 0) {
3037 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3038 "Failed to submit read-control"
3039 " URB status=%d",status);
3040 hdw->ctl_read_pend_flag = 0;
3041 goto done;
3042 }
3043 }
3044
3045 /* Start timer */
3046 add_timer(&timer);
3047
3048 /* Now wait for all I/O to complete */
3049 hdw->cmd_debug_state = 4;
3050 while (hdw->ctl_write_pend_flag || hdw->ctl_read_pend_flag) {
3051 wait_for_completion(&hdw->ctl_done);
3052 }
3053 hdw->cmd_debug_state = 5;
3054
3055 /* Stop timer */
3056 del_timer_sync(&timer);
3057
3058 hdw->cmd_debug_state = 6;
3059 status = 0;
3060
3061 if (hdw->ctl_timeout_flag) {
3062 status = -ETIMEDOUT;
3063 if (!probe_fl) {
3064 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3065 "Timed out control-write");
3066 }
3067 goto done;
3068 }
3069
3070 if (write_len) {
3071 /* Validate results of write request */
3072 if ((hdw->ctl_write_urb->status != 0) &&
3073 (hdw->ctl_write_urb->status != -ENOENT) &&
3074 (hdw->ctl_write_urb->status != -ESHUTDOWN) &&
3075 (hdw->ctl_write_urb->status != -ECONNRESET)) {
3076 /* USB subsystem is reporting some kind of failure
3077 on the write */
3078 status = hdw->ctl_write_urb->status;
3079 if (!probe_fl) {
3080 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3081 "control-write URB failure,"
3082 " status=%d",
3083 status);
3084 }
3085 goto done;
3086 }
3087 if (hdw->ctl_write_urb->actual_length < write_len) {
3088 /* Failed to write enough data */
3089 status = -EIO;
3090 if (!probe_fl) {
3091 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3092 "control-write URB short,"
3093 " expected=%d got=%d",
3094 write_len,
3095 hdw->ctl_write_urb->actual_length);
3096 }
3097 goto done;
3098 }
3099 }
3100 if (read_len) {
3101 /* Validate results of read request */
3102 if ((hdw->ctl_read_urb->status != 0) &&
3103 (hdw->ctl_read_urb->status != -ENOENT) &&
3104 (hdw->ctl_read_urb->status != -ESHUTDOWN) &&
3105 (hdw->ctl_read_urb->status != -ECONNRESET)) {
3106 /* USB subsystem is reporting some kind of failure
3107 on the read */
3108 status = hdw->ctl_read_urb->status;
3109 if (!probe_fl) {
3110 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3111 "control-read URB failure,"
3112 " status=%d",
3113 status);
3114 }
3115 goto done;
3116 }
3117 if (hdw->ctl_read_urb->actual_length < read_len) {
3118 /* Failed to read enough data */
3119 status = -EIO;
3120 if (!probe_fl) {
3121 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3122 "control-read URB short,"
3123 " expected=%d got=%d",
3124 read_len,
3125 hdw->ctl_read_urb->actual_length);
3126 }
3127 goto done;
3128 }
3129 /* Transfer retrieved data out from internal buffer */
3130 for (idx = 0; idx < read_len; idx++) {
3131 ((unsigned char *)read_data)[idx] =
3132 hdw->ctl_read_buffer[idx];
3133 }
3134 }
3135
3136 done:
3137
3138 hdw->cmd_debug_state = 0;
3139 if ((status < 0) && (!probe_fl)) {
Mike Isely681c7392007-11-26 01:48:52 -03003140 pvr2_hdw_render_useless(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03003141 }
3142 return status;
3143}
3144
3145
3146int pvr2_send_request(struct pvr2_hdw *hdw,
3147 void *write_data,unsigned int write_len,
3148 void *read_data,unsigned int read_len)
3149{
3150 return pvr2_send_request_ex(hdw,HZ*4,0,
3151 write_data,write_len,
3152 read_data,read_len);
3153}
3154
Mike Isely1c9d10d2008-03-28 05:38:54 -03003155
3156static int pvr2_issue_simple_cmd(struct pvr2_hdw *hdw,u32 cmdcode)
3157{
3158 int ret;
3159 unsigned int cnt = 1;
3160 unsigned int args = 0;
3161 LOCK_TAKE(hdw->ctl_lock);
3162 hdw->cmd_buffer[0] = cmdcode & 0xffu;
3163 args = (cmdcode >> 8) & 0xffu;
3164 args = (args > 2) ? 2 : args;
3165 if (args) {
3166 cnt += args;
3167 hdw->cmd_buffer[1] = (cmdcode >> 16) & 0xffu;
3168 if (args > 1) {
3169 hdw->cmd_buffer[2] = (cmdcode >> 24) & 0xffu;
3170 }
3171 }
3172 if (pvrusb2_debug & PVR2_TRACE_INIT) {
3173 unsigned int idx;
3174 unsigned int ccnt,bcnt;
3175 char tbuf[50];
3176 cmdcode &= 0xffu;
3177 bcnt = 0;
3178 ccnt = scnprintf(tbuf+bcnt,
3179 sizeof(tbuf)-bcnt,
3180 "Sending FX2 command 0x%x",cmdcode);
3181 bcnt += ccnt;
3182 for (idx = 0; idx < ARRAY_SIZE(pvr2_fx2cmd_desc); idx++) {
3183 if (pvr2_fx2cmd_desc[idx].id == cmdcode) {
3184 ccnt = scnprintf(tbuf+bcnt,
3185 sizeof(tbuf)-bcnt,
3186 " \"%s\"",
3187 pvr2_fx2cmd_desc[idx].desc);
3188 bcnt += ccnt;
3189 break;
3190 }
3191 }
3192 if (args) {
3193 ccnt = scnprintf(tbuf+bcnt,
3194 sizeof(tbuf)-bcnt,
3195 " (%u",hdw->cmd_buffer[1]);
3196 bcnt += ccnt;
3197 if (args > 1) {
3198 ccnt = scnprintf(tbuf+bcnt,
3199 sizeof(tbuf)-bcnt,
3200 ",%u",hdw->cmd_buffer[2]);
3201 bcnt += ccnt;
3202 }
3203 ccnt = scnprintf(tbuf+bcnt,
3204 sizeof(tbuf)-bcnt,
3205 ")");
3206 bcnt += ccnt;
3207 }
3208 pvr2_trace(PVR2_TRACE_INIT,"%.*s",bcnt,tbuf);
3209 }
3210 ret = pvr2_send_request(hdw,hdw->cmd_buffer,cnt,NULL,0);
3211 LOCK_GIVE(hdw->ctl_lock);
3212 return ret;
3213}
3214
3215
Mike Iselyd8554972006-06-26 20:58:46 -03003216int pvr2_write_register(struct pvr2_hdw *hdw, u16 reg, u32 data)
3217{
3218 int ret;
3219
3220 LOCK_TAKE(hdw->ctl_lock);
3221
Michael Krufky8d364362007-01-22 02:17:55 -03003222 hdw->cmd_buffer[0] = FX2CMD_REG_WRITE; /* write register prefix */
Mike Iselyd8554972006-06-26 20:58:46 -03003223 PVR2_DECOMPOSE_LE(hdw->cmd_buffer,1,data);
3224 hdw->cmd_buffer[5] = 0;
3225 hdw->cmd_buffer[6] = (reg >> 8) & 0xff;
3226 hdw->cmd_buffer[7] = reg & 0xff;
3227
3228
3229 ret = pvr2_send_request(hdw, hdw->cmd_buffer, 8, hdw->cmd_buffer, 0);
3230
3231 LOCK_GIVE(hdw->ctl_lock);
3232
3233 return ret;
3234}
3235
3236
Adrian Bunk07e337e2006-06-30 11:30:20 -03003237static int pvr2_read_register(struct pvr2_hdw *hdw, u16 reg, u32 *data)
Mike Iselyd8554972006-06-26 20:58:46 -03003238{
3239 int ret = 0;
3240
3241 LOCK_TAKE(hdw->ctl_lock);
3242
Michael Krufky8d364362007-01-22 02:17:55 -03003243 hdw->cmd_buffer[0] = FX2CMD_REG_READ; /* read register prefix */
Mike Iselyd8554972006-06-26 20:58:46 -03003244 hdw->cmd_buffer[1] = 0;
3245 hdw->cmd_buffer[2] = 0;
3246 hdw->cmd_buffer[3] = 0;
3247 hdw->cmd_buffer[4] = 0;
3248 hdw->cmd_buffer[5] = 0;
3249 hdw->cmd_buffer[6] = (reg >> 8) & 0xff;
3250 hdw->cmd_buffer[7] = reg & 0xff;
3251
3252 ret |= pvr2_send_request(hdw, hdw->cmd_buffer, 8, hdw->cmd_buffer, 4);
3253 *data = PVR2_COMPOSE_LE(hdw->cmd_buffer,0);
3254
3255 LOCK_GIVE(hdw->ctl_lock);
3256
3257 return ret;
3258}
3259
3260
Mike Isely681c7392007-11-26 01:48:52 -03003261void pvr2_hdw_render_useless(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03003262{
3263 if (!hdw->flag_ok) return;
Mike Isely681c7392007-11-26 01:48:52 -03003264 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3265 "Device being rendered inoperable");
Mike Iselyd8554972006-06-26 20:58:46 -03003266 if (hdw->vid_stream) {
Mike Iselya0fd1cb2006-06-30 11:35:28 -03003267 pvr2_stream_setup(hdw->vid_stream,NULL,0,0);
Mike Iselyd8554972006-06-26 20:58:46 -03003268 }
Mike Isely681c7392007-11-26 01:48:52 -03003269 hdw->flag_ok = 0;
3270 trace_stbit("flag_ok",hdw->flag_ok);
3271 pvr2_hdw_state_sched(hdw);
Mike Iselyd8554972006-06-26 20:58:46 -03003272}
3273
3274
3275void pvr2_hdw_device_reset(struct pvr2_hdw *hdw)
3276{
3277 int ret;
3278 pvr2_trace(PVR2_TRACE_INIT,"Performing a device reset...");
Mike Iselya0fd1cb2006-06-30 11:35:28 -03003279 ret = usb_lock_device_for_reset(hdw->usb_dev,NULL);
Mike Iselyd8554972006-06-26 20:58:46 -03003280 if (ret == 1) {
3281 ret = usb_reset_device(hdw->usb_dev);
3282 usb_unlock_device(hdw->usb_dev);
3283 } else {
3284 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3285 "Failed to lock USB device ret=%d",ret);
3286 }
3287 if (init_pause_msec) {
3288 pvr2_trace(PVR2_TRACE_INFO,
3289 "Waiting %u msec for hardware to settle",
3290 init_pause_msec);
3291 msleep(init_pause_msec);
3292 }
3293
3294}
3295
3296
3297void pvr2_hdw_cpureset_assert(struct pvr2_hdw *hdw,int val)
3298{
3299 char da[1];
3300 unsigned int pipe;
3301 int ret;
3302
3303 if (!hdw->usb_dev) return;
3304
3305 pvr2_trace(PVR2_TRACE_INIT,"cpureset_assert(%d)",val);
3306
3307 da[0] = val ? 0x01 : 0x00;
3308
3309 /* Write the CPUCS register on the 8051. The lsb of the register
3310 is the reset bit; a 1 asserts reset while a 0 clears it. */
3311 pipe = usb_sndctrlpipe(hdw->usb_dev, 0);
3312 ret = usb_control_msg(hdw->usb_dev,pipe,0xa0,0x40,0xe600,0,da,1,HZ);
3313 if (ret < 0) {
3314 pvr2_trace(PVR2_TRACE_ERROR_LEGS,
3315 "cpureset_assert(%d) error=%d",val,ret);
3316 pvr2_hdw_render_useless(hdw);
3317 }
3318}
3319
3320
3321int pvr2_hdw_cmd_deep_reset(struct pvr2_hdw *hdw)
3322{
Mike Isely1c9d10d2008-03-28 05:38:54 -03003323 return pvr2_issue_simple_cmd(hdw,FX2CMD_DEEP_RESET);
Mike Iselyd8554972006-06-26 20:58:46 -03003324}
3325
3326
Michael Krufkye1edb192008-04-22 14:45:39 -03003327int pvr2_hdw_cmd_powerup(struct pvr2_hdw *hdw)
3328{
Mike Isely1c9d10d2008-03-28 05:38:54 -03003329 return pvr2_issue_simple_cmd(hdw,FX2CMD_POWER_ON);
Michael Krufkye1edb192008-04-22 14:45:39 -03003330}
3331
Mike Isely1c9d10d2008-03-28 05:38:54 -03003332
Michael Krufkye1edb192008-04-22 14:45:39 -03003333int pvr2_hdw_cmd_powerdown(struct pvr2_hdw *hdw)
3334{
Mike Isely1c9d10d2008-03-28 05:38:54 -03003335 return pvr2_issue_simple_cmd(hdw,FX2CMD_POWER_OFF);
Michael Krufkye1edb192008-04-22 14:45:39 -03003336}
3337
Mike Iselyd8554972006-06-26 20:58:46 -03003338
3339int pvr2_hdw_cmd_decoder_reset(struct pvr2_hdw *hdw)
3340{
3341 if (!hdw->decoder_ctrl) {
3342 pvr2_trace(PVR2_TRACE_INIT,
3343 "Unable to reset decoder: nothing attached");
3344 return -ENOTTY;
3345 }
3346
3347 if (!hdw->decoder_ctrl->force_reset) {
3348 pvr2_trace(PVR2_TRACE_INIT,
3349 "Unable to reset decoder: not implemented");
3350 return -ENOTTY;
3351 }
3352
3353 pvr2_trace(PVR2_TRACE_INIT,
3354 "Requesting decoder reset");
3355 hdw->decoder_ctrl->force_reset(hdw->decoder_ctrl->ctxt);
3356 return 0;
3357}
3358
3359
Mike Isely62433e32008-04-22 14:45:40 -03003360static int pvr2_hdw_cmd_hcw_demod_reset(struct pvr2_hdw *hdw, int onoff)
Mike Isely84147f32008-04-22 14:45:40 -03003361{
Mike Isely1c9d10d2008-03-28 05:38:54 -03003362 hdw->flag_ok = !0;
3363 return pvr2_issue_simple_cmd(hdw,
3364 FX2CMD_HCW_DEMOD_RESETIN |
3365 (1 << 8) |
3366 ((onoff ? 1 : 0) << 16));
Mike Isely84147f32008-04-22 14:45:40 -03003367}
3368
Mike Isely84147f32008-04-22 14:45:40 -03003369
Mike Isely62433e32008-04-22 14:45:40 -03003370static int pvr2_hdw_cmd_onair_fe_power_ctrl(struct pvr2_hdw *hdw, int onoff)
Mike Isely84147f32008-04-22 14:45:40 -03003371{
Mike Isely1c9d10d2008-03-28 05:38:54 -03003372 hdw->flag_ok = !0;
3373 return pvr2_issue_simple_cmd(hdw,(onoff ?
3374 FX2CMD_ONAIR_DTV_POWER_ON :
3375 FX2CMD_ONAIR_DTV_POWER_OFF));
Mike Isely84147f32008-04-22 14:45:40 -03003376}
3377
Mike Isely62433e32008-04-22 14:45:40 -03003378
3379static int pvr2_hdw_cmd_onair_digital_path_ctrl(struct pvr2_hdw *hdw,
3380 int onoff)
Mike Isely84147f32008-04-22 14:45:40 -03003381{
Mike Isely1c9d10d2008-03-28 05:38:54 -03003382 return pvr2_issue_simple_cmd(hdw,(onoff ?
3383 FX2CMD_ONAIR_DTV_STREAMING_ON :
3384 FX2CMD_ONAIR_DTV_STREAMING_OFF));
Mike Isely84147f32008-04-22 14:45:40 -03003385}
3386
Mike Isely62433e32008-04-22 14:45:40 -03003387
3388static void pvr2_hdw_cmd_modeswitch(struct pvr2_hdw *hdw,int digitalFl)
3389{
3390 int cmode;
3391 /* Compare digital/analog desired setting with current setting. If
3392 they don't match, fix it... */
3393 cmode = (digitalFl ? PVR2_PATHWAY_DIGITAL : PVR2_PATHWAY_ANALOG);
3394 if (cmode == hdw->pathway_state) {
3395 /* They match; nothing to do */
3396 return;
3397 }
3398
3399 switch (hdw->hdw_desc->digital_control_scheme) {
3400 case PVR2_DIGITAL_SCHEME_HAUPPAUGE:
3401 pvr2_hdw_cmd_hcw_demod_reset(hdw,digitalFl);
3402 if (cmode == PVR2_PATHWAY_ANALOG) {
3403 /* If moving to analog mode, also force the decoder
3404 to reset. If no decoder is attached, then it's
3405 ok to ignore this because if/when the decoder
3406 attaches, it will reset itself at that time. */
3407 pvr2_hdw_cmd_decoder_reset(hdw);
3408 }
3409 break;
3410 case PVR2_DIGITAL_SCHEME_ONAIR:
3411 /* Supposedly we should always have the power on whether in
3412 digital or analog mode. But for now do what appears to
3413 work... */
Mike Iselybb0c2fe2008-03-28 05:41:19 -03003414 pvr2_hdw_cmd_onair_fe_power_ctrl(hdw,digitalFl);
Mike Isely62433e32008-04-22 14:45:40 -03003415 break;
3416 default: break;
3417 }
3418
Mike Isely1b9c18c2008-04-22 14:45:41 -03003419 pvr2_hdw_untrip_unlocked(hdw);
Mike Isely62433e32008-04-22 14:45:40 -03003420 hdw->pathway_state = cmode;
3421}
3422
3423
Adrian Bunke9b59f62008-05-10 04:35:24 -03003424static void pvr2_led_ctrl_hauppauge(struct pvr2_hdw *hdw, int onoff)
Mike Iselyc55a97d2008-04-22 14:45:41 -03003425{
3426 /* change some GPIO data
3427 *
3428 * note: bit d7 of dir appears to control the LED,
3429 * so we shut it off here.
3430 *
Mike Iselyc55a97d2008-04-22 14:45:41 -03003431 */
Mike Isely40381cb2008-04-22 14:45:42 -03003432 if (onoff) {
Mike Iselyc55a97d2008-04-22 14:45:41 -03003433 pvr2_hdw_gpio_chg_dir(hdw, 0xffffffff, 0x00000481);
Mike Isely40381cb2008-04-22 14:45:42 -03003434 } else {
Mike Iselyc55a97d2008-04-22 14:45:41 -03003435 pvr2_hdw_gpio_chg_dir(hdw, 0xffffffff, 0x00000401);
Mike Isely40381cb2008-04-22 14:45:42 -03003436 }
Mike Iselyc55a97d2008-04-22 14:45:41 -03003437 pvr2_hdw_gpio_chg_out(hdw, 0xffffffff, 0x00000000);
Mike Isely40381cb2008-04-22 14:45:42 -03003438}
Mike Iselyc55a97d2008-04-22 14:45:41 -03003439
Mike Isely40381cb2008-04-22 14:45:42 -03003440
3441typedef void (*led_method_func)(struct pvr2_hdw *,int);
3442
3443static led_method_func led_methods[] = {
3444 [PVR2_LED_SCHEME_HAUPPAUGE] = pvr2_led_ctrl_hauppauge,
3445};
3446
3447
3448/* Toggle LED */
3449static void pvr2_led_ctrl(struct pvr2_hdw *hdw,int onoff)
3450{
3451 unsigned int scheme_id;
3452 led_method_func fp;
3453
3454 if ((!onoff) == (!hdw->led_on)) return;
3455
3456 hdw->led_on = onoff != 0;
3457
3458 scheme_id = hdw->hdw_desc->led_scheme;
3459 if (scheme_id < ARRAY_SIZE(led_methods)) {
3460 fp = led_methods[scheme_id];
3461 } else {
3462 fp = NULL;
3463 }
3464
3465 if (fp) (*fp)(hdw,onoff);
Mike Iselyc55a97d2008-04-22 14:45:41 -03003466}
3467
3468
Mike Iselye61b6fc2006-07-18 22:42:18 -03003469/* Stop / start video stream transport */
Adrian Bunk07e337e2006-06-30 11:30:20 -03003470static int pvr2_hdw_cmd_usbstream(struct pvr2_hdw *hdw,int runFl)
Mike Iselyd8554972006-06-26 20:58:46 -03003471{
Mike Iselybb0c2fe2008-03-28 05:41:19 -03003472 int ret;
3473
3474 /* If we're in analog mode, then just issue the usual analog
3475 command. */
3476 if (hdw->pathway_state == PVR2_PATHWAY_ANALOG) {
3477 return pvr2_issue_simple_cmd(hdw,
3478 (runFl ?
3479 FX2CMD_STREAMING_ON :
3480 FX2CMD_STREAMING_OFF));
3481 /*Note: Not reached */
Mike Isely62433e32008-04-22 14:45:40 -03003482 }
Mike Iselybb0c2fe2008-03-28 05:41:19 -03003483
3484 if (hdw->pathway_state != PVR2_PATHWAY_DIGITAL) {
3485 /* Whoops, we don't know what mode we're in... */
3486 return -EINVAL;
3487 }
3488
3489 /* To get here we have to be in digital mode. The mechanism here
3490 is unfortunately different for different vendors. So we switch
3491 on the device's digital scheme attribute in order to figure out
3492 what to do. */
3493 switch (hdw->hdw_desc->digital_control_scheme) {
3494 case PVR2_DIGITAL_SCHEME_HAUPPAUGE:
3495 return pvr2_issue_simple_cmd(hdw,
3496 (runFl ?
3497 FX2CMD_HCW_DTV_STREAMING_ON :
3498 FX2CMD_HCW_DTV_STREAMING_OFF));
3499 case PVR2_DIGITAL_SCHEME_ONAIR:
3500 ret = pvr2_issue_simple_cmd(hdw,
3501 (runFl ?
3502 FX2CMD_STREAMING_ON :
3503 FX2CMD_STREAMING_OFF));
3504 if (ret) return ret;
3505 return pvr2_hdw_cmd_onair_digital_path_ctrl(hdw,runFl);
3506 default:
3507 return -EINVAL;
3508 }
Mike Iselyd8554972006-06-26 20:58:46 -03003509}
3510
3511
Mike Isely62433e32008-04-22 14:45:40 -03003512/* Evaluate whether or not state_pathway_ok can change */
3513static int state_eval_pathway_ok(struct pvr2_hdw *hdw)
3514{
3515 if (hdw->state_pathway_ok) {
3516 /* Nothing to do if pathway is already ok */
3517 return 0;
3518 }
3519 if (!hdw->state_pipeline_idle) {
3520 /* Not allowed to change anything if pipeline is not idle */
3521 return 0;
3522 }
3523 pvr2_hdw_cmd_modeswitch(hdw,hdw->input_val == PVR2_CVAL_INPUT_DTV);
3524 hdw->state_pathway_ok = !0;
Mike Iselye9db1ff2008-04-22 14:45:41 -03003525 trace_stbit("state_pathway_ok",hdw->state_pathway_ok);
Mike Isely62433e32008-04-22 14:45:40 -03003526 return !0;
3527}
3528
3529
Mike Isely681c7392007-11-26 01:48:52 -03003530/* Evaluate whether or not state_encoder_ok can change */
3531static int state_eval_encoder_ok(struct pvr2_hdw *hdw)
3532{
3533 if (hdw->state_encoder_ok) return 0;
3534 if (hdw->flag_tripped) return 0;
3535 if (hdw->state_encoder_run) return 0;
3536 if (hdw->state_encoder_config) return 0;
3537 if (hdw->state_decoder_run) return 0;
3538 if (hdw->state_usbstream_run) return 0;
Mike Isely72998b72008-04-03 04:51:19 -03003539 if (hdw->pathway_state == PVR2_PATHWAY_DIGITAL) {
3540 if (!hdw->hdw_desc->flag_digital_requires_cx23416) return 0;
3541 } else if (hdw->pathway_state != PVR2_PATHWAY_ANALOG) {
3542 return 0;
3543 }
3544
Mike Isely681c7392007-11-26 01:48:52 -03003545 if (pvr2_upload_firmware2(hdw) < 0) {
3546 hdw->flag_tripped = !0;
3547 trace_stbit("flag_tripped",hdw->flag_tripped);
3548 return !0;
3549 }
3550 hdw->state_encoder_ok = !0;
3551 trace_stbit("state_encoder_ok",hdw->state_encoder_ok);
3552 return !0;
3553}
3554
3555
3556/* Evaluate whether or not state_encoder_config can change */
3557static int state_eval_encoder_config(struct pvr2_hdw *hdw)
3558{
3559 if (hdw->state_encoder_config) {
3560 if (hdw->state_encoder_ok) {
3561 if (hdw->state_pipeline_req &&
3562 !hdw->state_pipeline_pause) return 0;
3563 }
3564 hdw->state_encoder_config = 0;
3565 hdw->state_encoder_waitok = 0;
3566 trace_stbit("state_encoder_waitok",hdw->state_encoder_waitok);
3567 /* paranoia - solve race if timer just completed */
3568 del_timer_sync(&hdw->encoder_wait_timer);
3569 } else {
Mike Isely62433e32008-04-22 14:45:40 -03003570 if (!hdw->state_pathway_ok ||
3571 (hdw->pathway_state != PVR2_PATHWAY_ANALOG) ||
3572 !hdw->state_encoder_ok ||
Mike Isely681c7392007-11-26 01:48:52 -03003573 !hdw->state_pipeline_idle ||
3574 hdw->state_pipeline_pause ||
3575 !hdw->state_pipeline_req ||
3576 !hdw->state_pipeline_config) {
3577 /* We must reset the enforced wait interval if
3578 anything has happened that might have disturbed
3579 the encoder. This should be a rare case. */
3580 if (timer_pending(&hdw->encoder_wait_timer)) {
3581 del_timer_sync(&hdw->encoder_wait_timer);
3582 }
3583 if (hdw->state_encoder_waitok) {
3584 /* Must clear the state - therefore we did
3585 something to a state bit and must also
3586 return true. */
3587 hdw->state_encoder_waitok = 0;
3588 trace_stbit("state_encoder_waitok",
3589 hdw->state_encoder_waitok);
3590 return !0;
3591 }
3592 return 0;
3593 }
3594 if (!hdw->state_encoder_waitok) {
3595 if (!timer_pending(&hdw->encoder_wait_timer)) {
3596 /* waitok flag wasn't set and timer isn't
3597 running. Check flag once more to avoid
3598 a race then start the timer. This is
3599 the point when we measure out a minimal
3600 quiet interval before doing something to
3601 the encoder. */
3602 if (!hdw->state_encoder_waitok) {
3603 hdw->encoder_wait_timer.expires =
3604 jiffies + (HZ*50/1000);
3605 add_timer(&hdw->encoder_wait_timer);
3606 }
3607 }
3608 /* We can't continue until we know we have been
3609 quiet for the interval measured by this
3610 timer. */
3611 return 0;
3612 }
3613 pvr2_encoder_configure(hdw);
3614 if (hdw->state_encoder_ok) hdw->state_encoder_config = !0;
3615 }
3616 trace_stbit("state_encoder_config",hdw->state_encoder_config);
3617 return !0;
3618}
3619
3620
Mike Iselyd913d632008-04-06 04:04:35 -03003621/* Return true if the encoder should not be running. */
3622static int state_check_disable_encoder_run(struct pvr2_hdw *hdw)
3623{
3624 if (!hdw->state_encoder_ok) {
3625 /* Encoder isn't healthy at the moment, so stop it. */
3626 return !0;
3627 }
3628 if (!hdw->state_pathway_ok) {
3629 /* Mode is not understood at the moment (i.e. it wants to
3630 change), so encoder must be stopped. */
3631 return !0;
3632 }
3633
3634 switch (hdw->pathway_state) {
3635 case PVR2_PATHWAY_ANALOG:
3636 if (!hdw->state_decoder_run) {
3637 /* We're in analog mode and the decoder is not
3638 running; thus the encoder should be stopped as
3639 well. */
3640 return !0;
3641 }
3642 break;
3643 case PVR2_PATHWAY_DIGITAL:
3644 if (hdw->state_encoder_runok) {
3645 /* This is a funny case. We're in digital mode so
3646 really the encoder should be stopped. However
3647 if it really is running, only kill it after
3648 runok has been set. This gives a chance for the
3649 onair quirk to function (encoder must run
3650 briefly first, at least once, before onair
3651 digital streaming can work). */
3652 return !0;
3653 }
3654 break;
3655 default:
3656 /* Unknown mode; so encoder should be stopped. */
3657 return !0;
3658 }
3659
3660 /* If we get here, we haven't found a reason to stop the
3661 encoder. */
3662 return 0;
3663}
3664
3665
3666/* Return true if the encoder should be running. */
3667static int state_check_enable_encoder_run(struct pvr2_hdw *hdw)
3668{
3669 if (!hdw->state_encoder_ok) {
3670 /* Don't run the encoder if it isn't healthy... */
3671 return 0;
3672 }
3673 if (!hdw->state_pathway_ok) {
3674 /* Don't run the encoder if we don't (yet) know what mode
3675 we need to be in... */
3676 return 0;
3677 }
3678
3679 switch (hdw->pathway_state) {
3680 case PVR2_PATHWAY_ANALOG:
3681 if (hdw->state_decoder_run) {
3682 /* In analog mode, if the decoder is running, then
3683 run the encoder. */
3684 return !0;
3685 }
3686 break;
3687 case PVR2_PATHWAY_DIGITAL:
3688 if ((hdw->hdw_desc->digital_control_scheme ==
3689 PVR2_DIGITAL_SCHEME_ONAIR) &&
3690 !hdw->state_encoder_runok) {
3691 /* This is a quirk. OnAir hardware won't stream
3692 digital until the encoder has been run at least
3693 once, for a minimal period of time (empiricially
3694 measured to be 1/4 second). So if we're on
3695 OnAir hardware and the encoder has never been
3696 run at all, then start the encoder. Normal
3697 state machine logic in the driver will
3698 automatically handle the remaining bits. */
3699 return !0;
3700 }
3701 break;
3702 default:
3703 /* For completeness (unknown mode; encoder won't run ever) */
3704 break;
3705 }
3706 /* If we get here, then we haven't found any reason to run the
3707 encoder, so don't run it. */
3708 return 0;
3709}
3710
3711
Mike Isely681c7392007-11-26 01:48:52 -03003712/* Evaluate whether or not state_encoder_run can change */
3713static int state_eval_encoder_run(struct pvr2_hdw *hdw)
3714{
3715 if (hdw->state_encoder_run) {
Mike Iselyd913d632008-04-06 04:04:35 -03003716 if (!state_check_disable_encoder_run(hdw)) return 0;
Mike Isely681c7392007-11-26 01:48:52 -03003717 if (hdw->state_encoder_ok) {
Mike Iselyd913d632008-04-06 04:04:35 -03003718 del_timer_sync(&hdw->encoder_run_timer);
Mike Isely681c7392007-11-26 01:48:52 -03003719 if (pvr2_encoder_stop(hdw) < 0) return !0;
3720 }
3721 hdw->state_encoder_run = 0;
3722 } else {
Mike Iselyd913d632008-04-06 04:04:35 -03003723 if (!state_check_enable_encoder_run(hdw)) return 0;
Mike Isely681c7392007-11-26 01:48:52 -03003724 if (pvr2_encoder_start(hdw) < 0) return !0;
3725 hdw->state_encoder_run = !0;
Mike Iselyd913d632008-04-06 04:04:35 -03003726 if (!hdw->state_encoder_runok) {
3727 hdw->encoder_run_timer.expires =
3728 jiffies + (HZ*250/1000);
3729 add_timer(&hdw->encoder_run_timer);
3730 }
Mike Isely681c7392007-11-26 01:48:52 -03003731 }
3732 trace_stbit("state_encoder_run",hdw->state_encoder_run);
3733 return !0;
3734}
3735
3736
3737/* Timeout function for quiescent timer. */
3738static void pvr2_hdw_quiescent_timeout(unsigned long data)
3739{
3740 struct pvr2_hdw *hdw = (struct pvr2_hdw *)data;
3741 hdw->state_decoder_quiescent = !0;
3742 trace_stbit("state_decoder_quiescent",hdw->state_decoder_quiescent);
3743 hdw->state_stale = !0;
3744 queue_work(hdw->workqueue,&hdw->workpoll);
3745}
3746
3747
3748/* Timeout function for encoder wait timer. */
3749static void pvr2_hdw_encoder_wait_timeout(unsigned long data)
3750{
3751 struct pvr2_hdw *hdw = (struct pvr2_hdw *)data;
3752 hdw->state_encoder_waitok = !0;
3753 trace_stbit("state_encoder_waitok",hdw->state_encoder_waitok);
3754 hdw->state_stale = !0;
3755 queue_work(hdw->workqueue,&hdw->workpoll);
3756}
3757
3758
Mike Iselyd913d632008-04-06 04:04:35 -03003759/* Timeout function for encoder run timer. */
3760static void pvr2_hdw_encoder_run_timeout(unsigned long data)
3761{
3762 struct pvr2_hdw *hdw = (struct pvr2_hdw *)data;
3763 if (!hdw->state_encoder_runok) {
3764 hdw->state_encoder_runok = !0;
3765 trace_stbit("state_encoder_runok",hdw->state_encoder_runok);
3766 hdw->state_stale = !0;
3767 queue_work(hdw->workqueue,&hdw->workpoll);
3768 }
3769}
3770
3771
Mike Isely681c7392007-11-26 01:48:52 -03003772/* Evaluate whether or not state_decoder_run can change */
3773static int state_eval_decoder_run(struct pvr2_hdw *hdw)
3774{
3775 if (hdw->state_decoder_run) {
3776 if (hdw->state_encoder_ok) {
3777 if (hdw->state_pipeline_req &&
Mike Isely62433e32008-04-22 14:45:40 -03003778 !hdw->state_pipeline_pause &&
3779 hdw->state_pathway_ok) return 0;
Mike Isely681c7392007-11-26 01:48:52 -03003780 }
3781 if (!hdw->flag_decoder_missed) {
3782 pvr2_decoder_enable(hdw,0);
3783 }
3784 hdw->state_decoder_quiescent = 0;
3785 hdw->state_decoder_run = 0;
3786 /* paranoia - solve race if timer just completed */
3787 del_timer_sync(&hdw->quiescent_timer);
3788 } else {
3789 if (!hdw->state_decoder_quiescent) {
3790 if (!timer_pending(&hdw->quiescent_timer)) {
3791 /* We don't do something about the
3792 quiescent timer until right here because
3793 we also want to catch cases where the
3794 decoder was already not running (like
3795 after initialization) as opposed to
3796 knowing that we had just stopped it.
3797 The second flag check is here to cover a
3798 race - the timer could have run and set
3799 this flag just after the previous check
3800 but before we did the pending check. */
3801 if (!hdw->state_decoder_quiescent) {
3802 hdw->quiescent_timer.expires =
3803 jiffies + (HZ*50/1000);
3804 add_timer(&hdw->quiescent_timer);
3805 }
3806 }
3807 /* Don't allow decoder to start again until it has
3808 been quiesced first. This little detail should
3809 hopefully further stabilize the encoder. */
3810 return 0;
3811 }
Mike Isely62433e32008-04-22 14:45:40 -03003812 if (!hdw->state_pathway_ok ||
3813 (hdw->pathway_state != PVR2_PATHWAY_ANALOG) ||
3814 !hdw->state_pipeline_req ||
Mike Isely681c7392007-11-26 01:48:52 -03003815 hdw->state_pipeline_pause ||
3816 !hdw->state_pipeline_config ||
3817 !hdw->state_encoder_config ||
3818 !hdw->state_encoder_ok) return 0;
3819 del_timer_sync(&hdw->quiescent_timer);
3820 if (hdw->flag_decoder_missed) return 0;
3821 if (pvr2_decoder_enable(hdw,!0) < 0) return 0;
3822 hdw->state_decoder_quiescent = 0;
3823 hdw->state_decoder_run = !0;
3824 }
3825 trace_stbit("state_decoder_quiescent",hdw->state_decoder_quiescent);
3826 trace_stbit("state_decoder_run",hdw->state_decoder_run);
3827 return !0;
3828}
3829
3830
3831/* Evaluate whether or not state_usbstream_run can change */
3832static int state_eval_usbstream_run(struct pvr2_hdw *hdw)
3833{
3834 if (hdw->state_usbstream_run) {
Mike Isely72998b72008-04-03 04:51:19 -03003835 int fl = !0;
Mike Isely62433e32008-04-22 14:45:40 -03003836 if (hdw->pathway_state == PVR2_PATHWAY_ANALOG) {
Mike Isely72998b72008-04-03 04:51:19 -03003837 fl = (hdw->state_encoder_ok &&
3838 hdw->state_encoder_run);
3839 } else if ((hdw->pathway_state == PVR2_PATHWAY_DIGITAL) &&
3840 (hdw->hdw_desc->flag_digital_requires_cx23416)) {
3841 fl = hdw->state_encoder_ok;
3842 }
3843 if (fl &&
3844 hdw->state_pipeline_req &&
3845 !hdw->state_pipeline_pause &&
3846 hdw->state_pathway_ok) {
3847 return 0;
Mike Isely681c7392007-11-26 01:48:52 -03003848 }
3849 pvr2_hdw_cmd_usbstream(hdw,0);
3850 hdw->state_usbstream_run = 0;
3851 } else {
Mike Isely62433e32008-04-22 14:45:40 -03003852 if (!hdw->state_pipeline_req ||
3853 hdw->state_pipeline_pause ||
3854 !hdw->state_pathway_ok) return 0;
3855 if (hdw->pathway_state == PVR2_PATHWAY_ANALOG) {
3856 if (!hdw->state_encoder_ok ||
3857 !hdw->state_encoder_run) return 0;
Mike Isely72998b72008-04-03 04:51:19 -03003858 } else if ((hdw->pathway_state == PVR2_PATHWAY_DIGITAL) &&
3859 (hdw->hdw_desc->flag_digital_requires_cx23416)) {
3860 if (!hdw->state_encoder_ok) return 0;
Mike Iselyd913d632008-04-06 04:04:35 -03003861 if (hdw->state_encoder_run) return 0;
3862 if (hdw->hdw_desc->digital_control_scheme ==
3863 PVR2_DIGITAL_SCHEME_ONAIR) {
3864 /* OnAir digital receivers won't stream
3865 unless the analog encoder has run first.
3866 Why? I have no idea. But don't even
3867 try until we know the analog side is
3868 known to have run. */
3869 if (!hdw->state_encoder_runok) return 0;
3870 }
Mike Isely62433e32008-04-22 14:45:40 -03003871 }
Mike Isely681c7392007-11-26 01:48:52 -03003872 if (pvr2_hdw_cmd_usbstream(hdw,!0) < 0) return 0;
3873 hdw->state_usbstream_run = !0;
3874 }
3875 trace_stbit("state_usbstream_run",hdw->state_usbstream_run);
3876 return !0;
3877}
3878
3879
3880/* Attempt to configure pipeline, if needed */
3881static int state_eval_pipeline_config(struct pvr2_hdw *hdw)
3882{
3883 if (hdw->state_pipeline_config ||
3884 hdw->state_pipeline_pause) return 0;
3885 pvr2_hdw_commit_execute(hdw);
3886 return !0;
3887}
3888
3889
3890/* Update pipeline idle and pipeline pause tracking states based on other
3891 inputs. This must be called whenever the other relevant inputs have
3892 changed. */
3893static int state_update_pipeline_state(struct pvr2_hdw *hdw)
3894{
3895 unsigned int st;
3896 int updatedFl = 0;
3897 /* Update pipeline state */
3898 st = !(hdw->state_encoder_run ||
3899 hdw->state_decoder_run ||
3900 hdw->state_usbstream_run ||
3901 (!hdw->state_decoder_quiescent));
3902 if (!st != !hdw->state_pipeline_idle) {
3903 hdw->state_pipeline_idle = st;
3904 updatedFl = !0;
3905 }
3906 if (hdw->state_pipeline_idle && hdw->state_pipeline_pause) {
3907 hdw->state_pipeline_pause = 0;
3908 updatedFl = !0;
3909 }
3910 return updatedFl;
3911}
3912
3913
3914typedef int (*state_eval_func)(struct pvr2_hdw *);
3915
3916/* Set of functions to be run to evaluate various states in the driver. */
Tobias Klauserebff0332008-04-22 14:45:45 -03003917static const state_eval_func eval_funcs[] = {
Mike Isely62433e32008-04-22 14:45:40 -03003918 state_eval_pathway_ok,
Mike Isely681c7392007-11-26 01:48:52 -03003919 state_eval_pipeline_config,
3920 state_eval_encoder_ok,
3921 state_eval_encoder_config,
3922 state_eval_decoder_run,
3923 state_eval_encoder_run,
3924 state_eval_usbstream_run,
3925};
3926
3927
3928/* Process various states and return true if we did anything interesting. */
3929static int pvr2_hdw_state_update(struct pvr2_hdw *hdw)
3930{
3931 unsigned int i;
3932 int state_updated = 0;
3933 int check_flag;
3934
3935 if (!hdw->state_stale) return 0;
3936 if ((hdw->fw1_state != FW1_STATE_OK) ||
3937 !hdw->flag_ok) {
3938 hdw->state_stale = 0;
3939 return !0;
3940 }
3941 /* This loop is the heart of the entire driver. It keeps trying to
3942 evaluate various bits of driver state until nothing changes for
3943 one full iteration. Each "bit of state" tracks some global
3944 aspect of the driver, e.g. whether decoder should run, if
3945 pipeline is configured, usb streaming is on, etc. We separately
3946 evaluate each of those questions based on other driver state to
3947 arrive at the correct running configuration. */
3948 do {
3949 check_flag = 0;
3950 state_update_pipeline_state(hdw);
3951 /* Iterate over each bit of state */
3952 for (i = 0; (i<ARRAY_SIZE(eval_funcs)) && hdw->flag_ok; i++) {
3953 if ((*eval_funcs[i])(hdw)) {
3954 check_flag = !0;
3955 state_updated = !0;
3956 state_update_pipeline_state(hdw);
3957 }
3958 }
3959 } while (check_flag && hdw->flag_ok);
3960 hdw->state_stale = 0;
3961 trace_stbit("state_stale",hdw->state_stale);
3962 return state_updated;
3963}
3964
3965
Mike Isely1cb03b72008-04-21 03:47:43 -03003966static unsigned int print_input_mask(unsigned int msk,
3967 char *buf,unsigned int acnt)
3968{
3969 unsigned int idx,ccnt;
3970 unsigned int tcnt = 0;
3971 for (idx = 0; idx < ARRAY_SIZE(control_values_input); idx++) {
3972 if (!((1 << idx) & msk)) continue;
3973 ccnt = scnprintf(buf+tcnt,
3974 acnt-tcnt,
3975 "%s%s",
3976 (tcnt ? ", " : ""),
3977 control_values_input[idx]);
3978 tcnt += ccnt;
3979 }
3980 return tcnt;
3981}
3982
3983
Mike Isely62433e32008-04-22 14:45:40 -03003984static const char *pvr2_pathway_state_name(int id)
3985{
3986 switch (id) {
3987 case PVR2_PATHWAY_ANALOG: return "analog";
3988 case PVR2_PATHWAY_DIGITAL: return "digital";
3989 default: return "unknown";
3990 }
3991}
3992
3993
Mike Isely681c7392007-11-26 01:48:52 -03003994static unsigned int pvr2_hdw_report_unlocked(struct pvr2_hdw *hdw,int which,
3995 char *buf,unsigned int acnt)
3996{
3997 switch (which) {
3998 case 0:
3999 return scnprintf(
4000 buf,acnt,
Mike Iselye9db1ff2008-04-22 14:45:41 -03004001 "driver:%s%s%s%s%s <mode=%s>",
Mike Isely681c7392007-11-26 01:48:52 -03004002 (hdw->flag_ok ? " <ok>" : " <fail>"),
4003 (hdw->flag_init_ok ? " <init>" : " <uninitialized>"),
4004 (hdw->flag_disconnected ? " <disconnected>" :
4005 " <connected>"),
4006 (hdw->flag_tripped ? " <tripped>" : ""),
Mike Isely62433e32008-04-22 14:45:40 -03004007 (hdw->flag_decoder_missed ? " <no decoder>" : ""),
4008 pvr2_pathway_state_name(hdw->pathway_state));
4009
Mike Isely681c7392007-11-26 01:48:52 -03004010 case 1:
4011 return scnprintf(
4012 buf,acnt,
4013 "pipeline:%s%s%s%s",
4014 (hdw->state_pipeline_idle ? " <idle>" : ""),
4015 (hdw->state_pipeline_config ?
4016 " <configok>" : " <stale>"),
4017 (hdw->state_pipeline_req ? " <req>" : ""),
4018 (hdw->state_pipeline_pause ? " <pause>" : ""));
4019 case 2:
4020 return scnprintf(
4021 buf,acnt,
Mike Isely62433e32008-04-22 14:45:40 -03004022 "worker:%s%s%s%s%s%s%s",
Mike Isely681c7392007-11-26 01:48:52 -03004023 (hdw->state_decoder_run ?
4024 " <decode:run>" :
4025 (hdw->state_decoder_quiescent ?
4026 "" : " <decode:stop>")),
4027 (hdw->state_decoder_quiescent ?
4028 " <decode:quiescent>" : ""),
4029 (hdw->state_encoder_ok ?
4030 "" : " <encode:init>"),
4031 (hdw->state_encoder_run ?
Mike Iselyd913d632008-04-06 04:04:35 -03004032 (hdw->state_encoder_runok ?
4033 " <encode:run>" :
4034 " <encode:firstrun>") :
4035 (hdw->state_encoder_runok ?
4036 " <encode:stop>" :
4037 " <encode:virgin>")),
Mike Isely681c7392007-11-26 01:48:52 -03004038 (hdw->state_encoder_config ?
4039 " <encode:configok>" :
4040 (hdw->state_encoder_waitok ?
Mike Iselyb9a37d92008-03-28 05:31:40 -03004041 "" : " <encode:waitok>")),
Mike Isely681c7392007-11-26 01:48:52 -03004042 (hdw->state_usbstream_run ?
Mike Isely62433e32008-04-22 14:45:40 -03004043 " <usb:run>" : " <usb:stop>"),
4044 (hdw->state_pathway_ok ?
Mike Iselye9db1ff2008-04-22 14:45:41 -03004045 " <pathway:ok>" : ""));
Mike Isely681c7392007-11-26 01:48:52 -03004046 case 3:
4047 return scnprintf(
4048 buf,acnt,
4049 "state: %s",
4050 pvr2_get_state_name(hdw->master_state));
Mike Iselyad0992e2008-03-28 05:34:45 -03004051 case 4: {
Mike Isely1cb03b72008-04-21 03:47:43 -03004052 unsigned int tcnt = 0;
4053 unsigned int ccnt;
4054
4055 ccnt = scnprintf(buf,
4056 acnt,
4057 "Hardware supported inputs: ");
4058 tcnt += ccnt;
4059 tcnt += print_input_mask(hdw->input_avail_mask,
4060 buf+tcnt,
4061 acnt-tcnt);
4062 if (hdw->input_avail_mask != hdw->input_allowed_mask) {
4063 ccnt = scnprintf(buf+tcnt,
4064 acnt-tcnt,
4065 "; allowed inputs: ");
4066 tcnt += ccnt;
4067 tcnt += print_input_mask(hdw->input_allowed_mask,
4068 buf+tcnt,
4069 acnt-tcnt);
4070 }
4071 return tcnt;
4072 }
4073 case 5: {
Mike Iselyad0992e2008-03-28 05:34:45 -03004074 struct pvr2_stream_stats stats;
4075 if (!hdw->vid_stream) break;
4076 pvr2_stream_get_stats(hdw->vid_stream,
4077 &stats,
4078 0);
4079 return scnprintf(
4080 buf,acnt,
4081 "Bytes streamed=%u"
4082 " URBs: queued=%u idle=%u ready=%u"
4083 " processed=%u failed=%u",
4084 stats.bytes_processed,
4085 stats.buffers_in_queue,
4086 stats.buffers_in_idle,
4087 stats.buffers_in_ready,
4088 stats.buffers_processed,
4089 stats.buffers_failed);
4090 }
Mike Isely681c7392007-11-26 01:48:52 -03004091 default: break;
4092 }
4093 return 0;
4094}
4095
4096
4097unsigned int pvr2_hdw_state_report(struct pvr2_hdw *hdw,
4098 char *buf,unsigned int acnt)
4099{
4100 unsigned int bcnt,ccnt,idx;
4101 bcnt = 0;
4102 LOCK_TAKE(hdw->big_lock);
4103 for (idx = 0; ; idx++) {
4104 ccnt = pvr2_hdw_report_unlocked(hdw,idx,buf,acnt);
4105 if (!ccnt) break;
4106 bcnt += ccnt; acnt -= ccnt; buf += ccnt;
4107 if (!acnt) break;
4108 buf[0] = '\n'; ccnt = 1;
4109 bcnt += ccnt; acnt -= ccnt; buf += ccnt;
4110 }
4111 LOCK_GIVE(hdw->big_lock);
4112 return bcnt;
4113}
4114
4115
4116static void pvr2_hdw_state_log_state(struct pvr2_hdw *hdw)
4117{
4118 char buf[128];
4119 unsigned int idx,ccnt;
4120
4121 for (idx = 0; ; idx++) {
4122 ccnt = pvr2_hdw_report_unlocked(hdw,idx,buf,sizeof(buf));
4123 if (!ccnt) break;
4124 printk(KERN_INFO "%s %.*s\n",hdw->name,ccnt,buf);
4125 }
4126}
4127
4128
4129/* Evaluate and update the driver's current state, taking various actions
4130 as appropriate for the update. */
4131static int pvr2_hdw_state_eval(struct pvr2_hdw *hdw)
4132{
4133 unsigned int st;
4134 int state_updated = 0;
4135 int callback_flag = 0;
Mike Isely1b9c18c2008-04-22 14:45:41 -03004136 int analog_mode;
Mike Isely681c7392007-11-26 01:48:52 -03004137
4138 pvr2_trace(PVR2_TRACE_STBITS,
4139 "Drive state check START");
4140 if (pvrusb2_debug & PVR2_TRACE_STBITS) {
4141 pvr2_hdw_state_log_state(hdw);
4142 }
4143
4144 /* Process all state and get back over disposition */
4145 state_updated = pvr2_hdw_state_update(hdw);
4146
Mike Isely1b9c18c2008-04-22 14:45:41 -03004147 analog_mode = (hdw->pathway_state != PVR2_PATHWAY_DIGITAL);
4148
Mike Isely681c7392007-11-26 01:48:52 -03004149 /* Update master state based upon all other states. */
4150 if (!hdw->flag_ok) {
4151 st = PVR2_STATE_DEAD;
4152 } else if (hdw->fw1_state != FW1_STATE_OK) {
4153 st = PVR2_STATE_COLD;
Mike Isely72998b72008-04-03 04:51:19 -03004154 } else if ((analog_mode ||
4155 hdw->hdw_desc->flag_digital_requires_cx23416) &&
4156 !hdw->state_encoder_ok) {
Mike Isely681c7392007-11-26 01:48:52 -03004157 st = PVR2_STATE_WARM;
Mike Isely1b9c18c2008-04-22 14:45:41 -03004158 } else if (hdw->flag_tripped ||
4159 (analog_mode && hdw->flag_decoder_missed)) {
Mike Isely681c7392007-11-26 01:48:52 -03004160 st = PVR2_STATE_ERROR;
Mike Isely62433e32008-04-22 14:45:40 -03004161 } else if (hdw->state_usbstream_run &&
Mike Isely1b9c18c2008-04-22 14:45:41 -03004162 (!analog_mode ||
Mike Isely62433e32008-04-22 14:45:40 -03004163 (hdw->state_encoder_run && hdw->state_decoder_run))) {
Mike Isely681c7392007-11-26 01:48:52 -03004164 st = PVR2_STATE_RUN;
4165 } else {
4166 st = PVR2_STATE_READY;
4167 }
4168 if (hdw->master_state != st) {
4169 pvr2_trace(PVR2_TRACE_STATE,
4170 "Device state change from %s to %s",
4171 pvr2_get_state_name(hdw->master_state),
4172 pvr2_get_state_name(st));
Mike Isely40381cb2008-04-22 14:45:42 -03004173 pvr2_led_ctrl(hdw,st == PVR2_STATE_RUN);
Mike Isely681c7392007-11-26 01:48:52 -03004174 hdw->master_state = st;
4175 state_updated = !0;
4176 callback_flag = !0;
4177 }
4178 if (state_updated) {
4179 /* Trigger anyone waiting on any state changes here. */
4180 wake_up(&hdw->state_wait_data);
4181 }
4182
4183 if (pvrusb2_debug & PVR2_TRACE_STBITS) {
4184 pvr2_hdw_state_log_state(hdw);
4185 }
4186 pvr2_trace(PVR2_TRACE_STBITS,
4187 "Drive state check DONE callback=%d",callback_flag);
4188
4189 return callback_flag;
4190}
4191
4192
4193/* Cause kernel thread to check / update driver state */
4194static void pvr2_hdw_state_sched(struct pvr2_hdw *hdw)
4195{
4196 if (hdw->state_stale) return;
4197 hdw->state_stale = !0;
4198 trace_stbit("state_stale",hdw->state_stale);
4199 queue_work(hdw->workqueue,&hdw->workpoll);
4200}
4201
4202
Mike Iselyd8554972006-06-26 20:58:46 -03004203int pvr2_hdw_gpio_get_dir(struct pvr2_hdw *hdw,u32 *dp)
4204{
4205 return pvr2_read_register(hdw,PVR2_GPIO_DIR,dp);
4206}
4207
4208
4209int pvr2_hdw_gpio_get_out(struct pvr2_hdw *hdw,u32 *dp)
4210{
4211 return pvr2_read_register(hdw,PVR2_GPIO_OUT,dp);
4212}
4213
4214
4215int pvr2_hdw_gpio_get_in(struct pvr2_hdw *hdw,u32 *dp)
4216{
4217 return pvr2_read_register(hdw,PVR2_GPIO_IN,dp);
4218}
4219
4220
4221int pvr2_hdw_gpio_chg_dir(struct pvr2_hdw *hdw,u32 msk,u32 val)
4222{
4223 u32 cval,nval;
4224 int ret;
4225 if (~msk) {
4226 ret = pvr2_read_register(hdw,PVR2_GPIO_DIR,&cval);
4227 if (ret) return ret;
4228 nval = (cval & ~msk) | (val & msk);
4229 pvr2_trace(PVR2_TRACE_GPIO,
4230 "GPIO direction changing 0x%x:0x%x"
4231 " from 0x%x to 0x%x",
4232 msk,val,cval,nval);
4233 } else {
4234 nval = val;
4235 pvr2_trace(PVR2_TRACE_GPIO,
4236 "GPIO direction changing to 0x%x",nval);
4237 }
4238 return pvr2_write_register(hdw,PVR2_GPIO_DIR,nval);
4239}
4240
4241
4242int pvr2_hdw_gpio_chg_out(struct pvr2_hdw *hdw,u32 msk,u32 val)
4243{
4244 u32 cval,nval;
4245 int ret;
4246 if (~msk) {
4247 ret = pvr2_read_register(hdw,PVR2_GPIO_OUT,&cval);
4248 if (ret) return ret;
4249 nval = (cval & ~msk) | (val & msk);
4250 pvr2_trace(PVR2_TRACE_GPIO,
4251 "GPIO output changing 0x%x:0x%x from 0x%x to 0x%x",
4252 msk,val,cval,nval);
4253 } else {
4254 nval = val;
4255 pvr2_trace(PVR2_TRACE_GPIO,
4256 "GPIO output changing to 0x%x",nval);
4257 }
4258 return pvr2_write_register(hdw,PVR2_GPIO_OUT,nval);
4259}
4260
4261
Mike Isely7fb20fa2008-04-22 14:45:37 -03004262unsigned int pvr2_hdw_get_input_available(struct pvr2_hdw *hdw)
4263{
4264 return hdw->input_avail_mask;
4265}
4266
4267
Mike Isely1cb03b72008-04-21 03:47:43 -03004268unsigned int pvr2_hdw_get_input_allowed(struct pvr2_hdw *hdw)
4269{
4270 return hdw->input_allowed_mask;
4271}
4272
4273
4274static int pvr2_hdw_set_input(struct pvr2_hdw *hdw,int v)
4275{
4276 if (hdw->input_val != v) {
4277 hdw->input_val = v;
4278 hdw->input_dirty = !0;
4279 }
4280
4281 /* Handle side effects - if we switch to a mode that needs the RF
4282 tuner, then select the right frequency choice as well and mark
4283 it dirty. */
4284 if (hdw->input_val == PVR2_CVAL_INPUT_RADIO) {
4285 hdw->freqSelector = 0;
4286 hdw->freqDirty = !0;
4287 } else if ((hdw->input_val == PVR2_CVAL_INPUT_TV) ||
4288 (hdw->input_val == PVR2_CVAL_INPUT_DTV)) {
4289 hdw->freqSelector = 1;
4290 hdw->freqDirty = !0;
4291 }
4292 return 0;
4293}
4294
4295
4296int pvr2_hdw_set_input_allowed(struct pvr2_hdw *hdw,
4297 unsigned int change_mask,
4298 unsigned int change_val)
4299{
4300 int ret = 0;
4301 unsigned int nv,m,idx;
4302 LOCK_TAKE(hdw->big_lock);
4303 do {
4304 nv = hdw->input_allowed_mask & ~change_mask;
4305 nv |= (change_val & change_mask);
4306 nv &= hdw->input_avail_mask;
4307 if (!nv) {
4308 /* No legal modes left; return error instead. */
4309 ret = -EPERM;
4310 break;
4311 }
4312 hdw->input_allowed_mask = nv;
4313 if ((1 << hdw->input_val) & hdw->input_allowed_mask) {
4314 /* Current mode is still in the allowed mask, so
4315 we're done. */
4316 break;
4317 }
4318 /* Select and switch to a mode that is still in the allowed
4319 mask */
4320 if (!hdw->input_allowed_mask) {
4321 /* Nothing legal; give up */
4322 break;
4323 }
4324 m = hdw->input_allowed_mask;
4325 for (idx = 0; idx < (sizeof(m) << 3); idx++) {
4326 if (!((1 << idx) & m)) continue;
4327 pvr2_hdw_set_input(hdw,idx);
4328 break;
4329 }
4330 } while (0);
4331 LOCK_GIVE(hdw->big_lock);
4332 return ret;
4333}
4334
4335
Mike Iselye61b6fc2006-07-18 22:42:18 -03004336/* Find I2C address of eeprom */
Adrian Bunk07e337e2006-06-30 11:30:20 -03004337static int pvr2_hdw_get_eeprom_addr(struct pvr2_hdw *hdw)
Mike Iselyd8554972006-06-26 20:58:46 -03004338{
4339 int result;
4340 LOCK_TAKE(hdw->ctl_lock); do {
Michael Krufky8d364362007-01-22 02:17:55 -03004341 hdw->cmd_buffer[0] = FX2CMD_GET_EEPROM_ADDR;
Mike Iselyd8554972006-06-26 20:58:46 -03004342 result = pvr2_send_request(hdw,
4343 hdw->cmd_buffer,1,
4344 hdw->cmd_buffer,1);
4345 if (result < 0) break;
4346 result = hdw->cmd_buffer[0];
4347 } while(0); LOCK_GIVE(hdw->ctl_lock);
4348 return result;
4349}
4350
4351
Mike Isely32ffa9a2006-09-23 22:26:52 -03004352int pvr2_hdw_register_access(struct pvr2_hdw *hdw,
Hans Verkuilf3d092b2007-02-23 20:55:14 -03004353 u32 match_type, u32 match_chip, u64 reg_id,
4354 int setFl,u64 *val_ptr)
Mike Isely32ffa9a2006-09-23 22:26:52 -03004355{
4356#ifdef CONFIG_VIDEO_ADV_DEBUG
Mike Isely32ffa9a2006-09-23 22:26:52 -03004357 struct pvr2_i2c_client *cp;
4358 struct v4l2_register req;
Mike Isely6d988162006-09-28 17:53:49 -03004359 int stat = 0;
4360 int okFl = 0;
Mike Isely32ffa9a2006-09-23 22:26:52 -03004361
Mike Isely201f5c92007-01-28 16:08:36 -03004362 if (!capable(CAP_SYS_ADMIN)) return -EPERM;
4363
Hans Verkuilf3d092b2007-02-23 20:55:14 -03004364 req.match_type = match_type;
4365 req.match_chip = match_chip;
Mike Isely32ffa9a2006-09-23 22:26:52 -03004366 req.reg = reg_id;
4367 if (setFl) req.val = *val_ptr;
4368 mutex_lock(&hdw->i2c_list_lock); do {
Trent Piephoe77e2c22007-10-10 05:37:42 -03004369 list_for_each_entry(cp, &hdw->i2c_clients, list) {
Mike Isely8481a752007-04-27 12:31:31 -03004370 if (!v4l2_chip_match_i2c_client(
4371 cp->client,
4372 req.match_type, req.match_chip)) {
Hans Verkuilf3d092b2007-02-23 20:55:14 -03004373 continue;
4374 }
Mike Isely32ffa9a2006-09-23 22:26:52 -03004375 stat = pvr2_i2c_client_cmd(
Trent Piepho52ebc762007-01-23 22:38:13 -03004376 cp,(setFl ? VIDIOC_DBG_S_REGISTER :
4377 VIDIOC_DBG_G_REGISTER),&req);
Mike Isely32ffa9a2006-09-23 22:26:52 -03004378 if (!setFl) *val_ptr = req.val;
Mike Isely6d988162006-09-28 17:53:49 -03004379 okFl = !0;
4380 break;
Mike Isely32ffa9a2006-09-23 22:26:52 -03004381 }
4382 } while (0); mutex_unlock(&hdw->i2c_list_lock);
Mike Isely6d988162006-09-28 17:53:49 -03004383 if (okFl) {
4384 return stat;
4385 }
Mike Isely32ffa9a2006-09-23 22:26:52 -03004386 return -EINVAL;
4387#else
4388 return -ENOSYS;
4389#endif
4390}
4391
4392
Mike Iselyd8554972006-06-26 20:58:46 -03004393/*
4394 Stuff for Emacs to see, in order to encourage consistent editing style:
4395 *** Local Variables: ***
4396 *** mode: c ***
4397 *** fill-column: 75 ***
4398 *** tab-width: 8 ***
4399 *** c-basic-offset: 8 ***
4400 *** End: ***
4401 */