Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
bt819.c
Go to the documentation of this file.
1 /*
2  * bt819 - BT819A VideoStream Decoder (Rockwell Part)
3  *
4  * Copyright (C) 1999 Mike Bernson <[email protected]>
5  * Copyright (C) 1998 Dave Perks <[email protected]>
6  *
7  * Modifications for LML33/DC10plus unified driver
8  * Copyright (C) 2000 Serguei Miridonov <[email protected]>
9  *
10  * Changes by Ronald Bultje <[email protected]>
11  * - moved over to linux>=2.4.x i2c protocol (9/9/2002)
12  *
13  * This code was modify/ported from the saa7111 driver written
14  * by Dave Perks.
15  *
16  * This program is free software; you can redistribute it and/or modify
17  * it under the terms of the GNU General Public License as published by
18  * the Free Software Foundation; either version 2 of the License, or
19  * (at your option) any later version.
20  *
21  * This program is distributed in the hope that it will be useful,
22  * but WITHOUT ANY WARRANTY; without even the implied warranty of
23  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24  * GNU General Public License for more details.
25  *
26  * You should have received a copy of the GNU General Public License
27  * along with this program; if not, write to the Free Software
28  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29  */
30 
31 #include <linux/module.h>
32 #include <linux/types.h>
33 #include <linux/ioctl.h>
34 #include <linux/delay.h>
35 #include <linux/i2c.h>
36 #include <linux/videodev2.h>
37 #include <linux/slab.h>
38 #include <media/v4l2-device.h>
39 #include <media/v4l2-chip-ident.h>
40 #include <media/v4l2-ctrls.h>
41 #include <media/bt819.h>
42 
43 MODULE_DESCRIPTION("Brooktree-819 video decoder driver");
44 MODULE_AUTHOR("Mike Bernson & Dave Perks");
45 MODULE_LICENSE("GPL");
46 
47 static int debug;
48 module_param(debug, int, 0);
49 MODULE_PARM_DESC(debug, "Debug level (0-1)");
50 
51 
52 /* ----------------------------------------------------------------------- */
53 
54 struct bt819 {
55  struct v4l2_subdev sd;
57  unsigned char reg[32];
58 
60  int ident;
61  int input;
62  int enable;
63 };
64 
65 static inline struct bt819 *to_bt819(struct v4l2_subdev *sd)
66 {
67  return container_of(sd, struct bt819, sd);
68 }
69 
70 static inline struct v4l2_subdev *to_sd(struct v4l2_ctrl *ctrl)
71 {
72  return &container_of(ctrl->handler, struct bt819, hdl)->sd;
73 }
74 
75 struct timing {
76  int hactive;
77  int hdelay;
78  int vactive;
79  int vdelay;
80  int hscale;
81  int vscale;
82 };
83 
84 /* for values, see the bt819 datasheet */
85 static struct timing timing_data[] = {
86  {864 - 24, 20, 625 - 2, 1, 0x0504, 0x0000},
87  {858 - 24, 20, 525 - 2, 1, 0x00f8, 0x0000},
88 };
89 
90 /* ----------------------------------------------------------------------- */
91 
92 static inline int bt819_write(struct bt819 *decoder, u8 reg, u8 value)
93 {
94  struct i2c_client *client = v4l2_get_subdevdata(&decoder->sd);
95 
96  decoder->reg[reg] = value;
97  return i2c_smbus_write_byte_data(client, reg, value);
98 }
99 
100 static inline int bt819_setbit(struct bt819 *decoder, u8 reg, u8 bit, u8 value)
101 {
102  return bt819_write(decoder, reg,
103  (decoder->reg[reg] & ~(1 << bit)) | (value ? (1 << bit) : 0));
104 }
105 
106 static int bt819_write_block(struct bt819 *decoder, const u8 *data, unsigned int len)
107 {
108  struct i2c_client *client = v4l2_get_subdevdata(&decoder->sd);
109  int ret = -1;
110  u8 reg;
111 
112  /* the bt819 has an autoincrement function, use it if
113  * the adapter understands raw I2C */
114  if (i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
115  /* do raw I2C, not smbus compatible */
116  u8 block_data[32];
117  int block_len;
118 
119  while (len >= 2) {
120  block_len = 0;
121  block_data[block_len++] = reg = data[0];
122  do {
123  block_data[block_len++] =
124  decoder->reg[reg++] = data[1];
125  len -= 2;
126  data += 2;
127  } while (len >= 2 && data[0] == reg && block_len < 32);
128  ret = i2c_master_send(client, block_data, block_len);
129  if (ret < 0)
130  break;
131  }
132  } else {
133  /* do some slow I2C emulation kind of thing */
134  while (len >= 2) {
135  reg = *data++;
136  ret = bt819_write(decoder, reg, *data++);
137  if (ret < 0)
138  break;
139  len -= 2;
140  }
141  }
142 
143  return ret;
144 }
145 
146 static inline int bt819_read(struct bt819 *decoder, u8 reg)
147 {
148  struct i2c_client *client = v4l2_get_subdevdata(&decoder->sd);
149 
150  return i2c_smbus_read_byte_data(client, reg);
151 }
152 
153 static int bt819_init(struct v4l2_subdev *sd)
154 {
155  static unsigned char init[] = {
156  /*0x1f, 0x00,*/ /* Reset */
157  0x01, 0x59, /* 0x01 input format */
158  0x02, 0x00, /* 0x02 temporal decimation */
159  0x03, 0x12, /* 0x03 Cropping msb */
160  0x04, 0x16, /* 0x04 Vertical Delay, lsb */
161  0x05, 0xe0, /* 0x05 Vertical Active lsb */
162  0x06, 0x80, /* 0x06 Horizontal Delay lsb */
163  0x07, 0xd0, /* 0x07 Horizontal Active lsb */
164  0x08, 0x00, /* 0x08 Horizontal Scaling msb */
165  0x09, 0xf8, /* 0x09 Horizontal Scaling lsb */
166  0x0a, 0x00, /* 0x0a Brightness control */
167  0x0b, 0x30, /* 0x0b Miscellaneous control */
168  0x0c, 0xd8, /* 0x0c Luma Gain lsb */
169  0x0d, 0xfe, /* 0x0d Chroma Gain (U) lsb */
170  0x0e, 0xb4, /* 0x0e Chroma Gain (V) msb */
171  0x0f, 0x00, /* 0x0f Hue control */
172  0x12, 0x04, /* 0x12 Output Format */
173  0x13, 0x20, /* 0x13 Vertial Scaling msb 0x00
174  chroma comb OFF, line drop scaling, interlace scaling
175  BUG? Why does turning the chroma comb on fuck up color?
176  Bug in the bt819 stepping on my board?
177  */
178  0x14, 0x00, /* 0x14 Vertial Scaling lsb */
179  0x16, 0x07, /* 0x16 Video Timing Polarity
180  ACTIVE=active low
181  FIELD: high=odd,
182  vreset=active high,
183  hreset=active high */
184  0x18, 0x68, /* 0x18 AGC Delay */
185  0x19, 0x5d, /* 0x19 Burst Gate Delay */
186  0x1a, 0x80, /* 0x1a ADC Interface */
187  };
188 
189  struct bt819 *decoder = to_bt819(sd);
190  struct timing *timing = &timing_data[(decoder->norm & V4L2_STD_525_60) ? 1 : 0];
191 
192  init[0x03 * 2 - 1] =
193  (((timing->vdelay >> 8) & 0x03) << 6) |
194  (((timing->vactive >> 8) & 0x03) << 4) |
195  (((timing->hdelay >> 8) & 0x03) << 2) |
196  ((timing->hactive >> 8) & 0x03);
197  init[0x04 * 2 - 1] = timing->vdelay & 0xff;
198  init[0x05 * 2 - 1] = timing->vactive & 0xff;
199  init[0x06 * 2 - 1] = timing->hdelay & 0xff;
200  init[0x07 * 2 - 1] = timing->hactive & 0xff;
201  init[0x08 * 2 - 1] = timing->hscale >> 8;
202  init[0x09 * 2 - 1] = timing->hscale & 0xff;
203  /* 0x15 in array is address 0x19 */
204  init[0x15 * 2 - 1] = (decoder->norm & V4L2_STD_625_50) ? 115 : 93; /* Chroma burst delay */
205  /* reset */
206  bt819_write(decoder, 0x1f, 0x00);
207  mdelay(1);
208 
209  /* init */
210  return bt819_write_block(decoder, init, sizeof(init));
211 }
212 
213 /* ----------------------------------------------------------------------- */
214 
215 static int bt819_status(struct v4l2_subdev *sd, u32 *pstatus, v4l2_std_id *pstd)
216 {
217  struct bt819 *decoder = to_bt819(sd);
218  int status = bt819_read(decoder, 0x00);
221 
222  if ((status & 0x80))
223  res = 0;
224 
225  if ((status & 0x10))
226  std = V4L2_STD_PAL;
227  else
228  std = V4L2_STD_NTSC;
229  if (pstd)
230  *pstd = std;
231  if (pstatus)
232  *pstatus = res;
233 
234  v4l2_dbg(1, debug, sd, "get status %x\n", status);
235  return 0;
236 }
237 
238 static int bt819_querystd(struct v4l2_subdev *sd, v4l2_std_id *std)
239 {
240  return bt819_status(sd, NULL, std);
241 }
242 
243 static int bt819_g_input_status(struct v4l2_subdev *sd, u32 *status)
244 {
245  return bt819_status(sd, status, NULL);
246 }
247 
248 static int bt819_s_std(struct v4l2_subdev *sd, v4l2_std_id std)
249 {
250  struct bt819 *decoder = to_bt819(sd);
251  struct timing *timing = NULL;
252 
253  v4l2_dbg(1, debug, sd, "set norm %llx\n", (unsigned long long)std);
254 
255  if (sd->v4l2_dev == NULL || sd->v4l2_dev->notify == NULL)
256  v4l2_err(sd, "no notify found!\n");
257 
258  if (std & V4L2_STD_NTSC) {
260  bt819_setbit(decoder, 0x01, 0, 1);
261  bt819_setbit(decoder, 0x01, 1, 0);
262  bt819_setbit(decoder, 0x01, 5, 0);
263  bt819_write(decoder, 0x18, 0x68);
264  bt819_write(decoder, 0x19, 0x5d);
265  /* bt819_setbit(decoder, 0x1a, 5, 1); */
266  timing = &timing_data[1];
267  } else if (std & V4L2_STD_PAL) {
269  bt819_setbit(decoder, 0x01, 0, 1);
270  bt819_setbit(decoder, 0x01, 1, 1);
271  bt819_setbit(decoder, 0x01, 5, 1);
272  bt819_write(decoder, 0x18, 0x7f);
273  bt819_write(decoder, 0x19, 0x72);
274  /* bt819_setbit(decoder, 0x1a, 5, 0); */
275  timing = &timing_data[0];
276  } else {
277  v4l2_dbg(1, debug, sd, "unsupported norm %llx\n",
278  (unsigned long long)std);
279  return -EINVAL;
280  }
281  bt819_write(decoder, 0x03,
282  (((timing->vdelay >> 8) & 0x03) << 6) |
283  (((timing->vactive >> 8) & 0x03) << 4) |
284  (((timing->hdelay >> 8) & 0x03) << 2) |
285  ((timing->hactive >> 8) & 0x03));
286  bt819_write(decoder, 0x04, timing->vdelay & 0xff);
287  bt819_write(decoder, 0x05, timing->vactive & 0xff);
288  bt819_write(decoder, 0x06, timing->hdelay & 0xff);
289  bt819_write(decoder, 0x07, timing->hactive & 0xff);
290  bt819_write(decoder, 0x08, (timing->hscale >> 8) & 0xff);
291  bt819_write(decoder, 0x09, timing->hscale & 0xff);
292  decoder->norm = std;
294  return 0;
295 }
296 
297 static int bt819_s_routing(struct v4l2_subdev *sd,
298  u32 input, u32 output, u32 config)
299 {
300  struct bt819 *decoder = to_bt819(sd);
301 
302  v4l2_dbg(1, debug, sd, "set input %x\n", input);
303 
304  if (input > 7)
305  return -EINVAL;
306 
307  if (sd->v4l2_dev == NULL || sd->v4l2_dev->notify == NULL)
308  v4l2_err(sd, "no notify found!\n");
309 
310  if (decoder->input != input) {
312  decoder->input = input;
313  /* select mode */
314  if (decoder->input == 0) {
315  bt819_setbit(decoder, 0x0b, 6, 0);
316  bt819_setbit(decoder, 0x1a, 1, 1);
317  } else {
318  bt819_setbit(decoder, 0x0b, 6, 1);
319  bt819_setbit(decoder, 0x1a, 1, 0);
320  }
322  }
323  return 0;
324 }
325 
326 static int bt819_s_stream(struct v4l2_subdev *sd, int enable)
327 {
328  struct bt819 *decoder = to_bt819(sd);
329 
330  v4l2_dbg(1, debug, sd, "enable output %x\n", enable);
331 
332  if (decoder->enable != enable) {
333  decoder->enable = enable;
334  bt819_setbit(decoder, 0x16, 7, !enable);
335  }
336  return 0;
337 }
338 
339 static int bt819_s_ctrl(struct v4l2_ctrl *ctrl)
340 {
341  struct v4l2_subdev *sd = to_sd(ctrl);
342  struct bt819 *decoder = to_bt819(sd);
343  int temp;
344 
345  switch (ctrl->id) {
346  case V4L2_CID_BRIGHTNESS:
347  bt819_write(decoder, 0x0a, ctrl->val);
348  break;
349 
350  case V4L2_CID_CONTRAST:
351  bt819_write(decoder, 0x0c, ctrl->val & 0xff);
352  bt819_setbit(decoder, 0x0b, 2, ((ctrl->val >> 8) & 0x01));
353  break;
354 
355  case V4L2_CID_SATURATION:
356  bt819_write(decoder, 0x0d, (ctrl->val >> 7) & 0xff);
357  bt819_setbit(decoder, 0x0b, 1, ((ctrl->val >> 15) & 0x01));
358 
359  /* Ratio between U gain and V gain must stay the same as
360  the ratio between the default U and V gain values. */
361  temp = (ctrl->val * 180) / 254;
362  bt819_write(decoder, 0x0e, (temp >> 7) & 0xff);
363  bt819_setbit(decoder, 0x0b, 0, (temp >> 15) & 0x01);
364  break;
365 
366  case V4L2_CID_HUE:
367  bt819_write(decoder, 0x0f, ctrl->val);
368  break;
369 
370  default:
371  return -EINVAL;
372  }
373  return 0;
374 }
375 
376 static int bt819_g_chip_ident(struct v4l2_subdev *sd, struct v4l2_dbg_chip_ident *chip)
377 {
378  struct bt819 *decoder = to_bt819(sd);
379  struct i2c_client *client = v4l2_get_subdevdata(sd);
380 
381  return v4l2_chip_ident_i2c_client(client, chip, decoder->ident, 0);
382 }
383 
384 /* ----------------------------------------------------------------------- */
385 
386 static const struct v4l2_ctrl_ops bt819_ctrl_ops = {
387  .s_ctrl = bt819_s_ctrl,
388 };
389 
390 static const struct v4l2_subdev_core_ops bt819_core_ops = {
391  .g_chip_ident = bt819_g_chip_ident,
392  .g_ext_ctrls = v4l2_subdev_g_ext_ctrls,
393  .try_ext_ctrls = v4l2_subdev_try_ext_ctrls,
394  .s_ext_ctrls = v4l2_subdev_s_ext_ctrls,
395  .g_ctrl = v4l2_subdev_g_ctrl,
396  .s_ctrl = v4l2_subdev_s_ctrl,
397  .queryctrl = v4l2_subdev_queryctrl,
398  .querymenu = v4l2_subdev_querymenu,
399  .s_std = bt819_s_std,
400 };
401 
402 static const struct v4l2_subdev_video_ops bt819_video_ops = {
403  .s_routing = bt819_s_routing,
404  .s_stream = bt819_s_stream,
405  .querystd = bt819_querystd,
406  .g_input_status = bt819_g_input_status,
407 };
408 
409 static const struct v4l2_subdev_ops bt819_ops = {
410  .core = &bt819_core_ops,
411  .video = &bt819_video_ops,
412 };
413 
414 /* ----------------------------------------------------------------------- */
415 
416 static int bt819_probe(struct i2c_client *client,
417  const struct i2c_device_id *id)
418 {
419  int i, ver;
420  struct bt819 *decoder;
421  struct v4l2_subdev *sd;
422  const char *name;
423 
424  /* Check if the adapter supports the needed features */
425  if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_BYTE_DATA))
426  return -ENODEV;
427 
428  decoder = kzalloc(sizeof(struct bt819), GFP_KERNEL);
429  if (decoder == NULL)
430  return -ENOMEM;
431  sd = &decoder->sd;
432  v4l2_i2c_subdev_init(sd, client, &bt819_ops);
433 
434  ver = bt819_read(decoder, 0x17);
435  switch (ver & 0xf0) {
436  case 0x70:
437  name = "bt819a";
438  decoder->ident = V4L2_IDENT_BT819A;
439  break;
440  case 0x60:
441  name = "bt817a";
442  decoder->ident = V4L2_IDENT_BT817A;
443  break;
444  case 0x20:
445  name = "bt815a";
446  decoder->ident = V4L2_IDENT_BT815A;
447  break;
448  default:
449  v4l2_dbg(1, debug, sd,
450  "unknown chip version 0x%02x\n", ver);
451  return -ENODEV;
452  }
453 
454  v4l_info(client, "%s found @ 0x%x (%s)\n", name,
455  client->addr << 1, client->adapter->name);
456 
457  decoder->norm = V4L2_STD_NTSC;
458  decoder->input = 0;
459  decoder->enable = 1;
460 
461  i = bt819_init(sd);
462  if (i < 0)
463  v4l2_dbg(1, debug, sd, "init status %d\n", i);
464 
465  v4l2_ctrl_handler_init(&decoder->hdl, 4);
466  v4l2_ctrl_new_std(&decoder->hdl, &bt819_ctrl_ops,
467  V4L2_CID_BRIGHTNESS, -128, 127, 1, 0);
468  v4l2_ctrl_new_std(&decoder->hdl, &bt819_ctrl_ops,
469  V4L2_CID_CONTRAST, 0, 511, 1, 0xd8);
470  v4l2_ctrl_new_std(&decoder->hdl, &bt819_ctrl_ops,
471  V4L2_CID_SATURATION, 0, 511, 1, 0xfe);
472  v4l2_ctrl_new_std(&decoder->hdl, &bt819_ctrl_ops,
473  V4L2_CID_HUE, -128, 127, 1, 0);
474  sd->ctrl_handler = &decoder->hdl;
475  if (decoder->hdl.error) {
476  int err = decoder->hdl.error;
477 
478  v4l2_ctrl_handler_free(&decoder->hdl);
479  kfree(decoder);
480  return err;
481  }
482  v4l2_ctrl_handler_setup(&decoder->hdl);
483  return 0;
484 }
485 
486 static int bt819_remove(struct i2c_client *client)
487 {
488  struct v4l2_subdev *sd = i2c_get_clientdata(client);
489  struct bt819 *decoder = to_bt819(sd);
490 
492  v4l2_ctrl_handler_free(&decoder->hdl);
493  kfree(decoder);
494  return 0;
495 }
496 
497 /* ----------------------------------------------------------------------- */
498 
499 static const struct i2c_device_id bt819_id[] = {
500  { "bt819a", 0 },
501  { "bt817a", 0 },
502  { "bt815a", 0 },
503  { }
504 };
505 MODULE_DEVICE_TABLE(i2c, bt819_id);
506 
507 static struct i2c_driver bt819_driver = {
508  .driver = {
509  .owner = THIS_MODULE,
510  .name = "bt819",
511  },
512  .probe = bt819_probe,
513  .remove = bt819_remove,
514  .id_table = bt819_id,
515 };
516 
517 module_i2c_driver(bt819_driver);