1 /* 2 * bt856 - BT856A Digital Video Encoder (Rockwell Part) 3 * 4 * Copyright (C) 1999 Mike Bernson <mike@mlb.org> 5 * Copyright (C) 1998 Dave Perks <dperks@ibm.net> 6 * 7 * Modifications for LML33/DC10plus unified driver 8 * Copyright (C) 2000 Serguei Miridonov <mirsev@cicese.mx> 9 * 10 * This code was modify/ported from the saa7111 driver written 11 * by Dave Perks. 12 * 13 * Changes by Ronald Bultje <rbultje@ronald.bitfreak.net> 14 * - moved over to linux>=2.4.x i2c protocol (9/9/2002) 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 27 #include <linux/module.h> 28 #include <linux/types.h> 29 #include <linux/slab.h> 30 #include <linux/ioctl.h> 31 #include <linux/uaccess.h> 32 #include <linux/i2c.h> 33 #include <linux/videodev2.h> 34 #include <media/v4l2-device.h> 35 36 MODULE_DESCRIPTION("Brooktree-856A video encoder driver"); 37 MODULE_AUTHOR("Mike Bernson & Dave Perks"); 38 MODULE_LICENSE("GPL"); 39 40 static int debug; 41 module_param(debug, int, 0); 42 MODULE_PARM_DESC(debug, "Debug level (0-1)"); 43 44 45 /* ----------------------------------------------------------------------- */ 46 47 #define BT856_REG_OFFSET 0xDA 48 #define BT856_NR_REG 6 49 50 struct bt856 { 51 struct v4l2_subdev sd; 52 unsigned char reg[BT856_NR_REG]; 53 54 v4l2_std_id norm; 55 }; 56 57 static inline struct bt856 *to_bt856(struct v4l2_subdev *sd) 58 { 59 return container_of(sd, struct bt856, sd); 60 } 61 62 /* ----------------------------------------------------------------------- */ 63 64 static inline int bt856_write(struct bt856 *encoder, u8 reg, u8 value) 65 { 66 struct i2c_client *client = v4l2_get_subdevdata(&encoder->sd); 67 68 encoder->reg[reg - BT856_REG_OFFSET] = value; 69 return i2c_smbus_write_byte_data(client, reg, value); 70 } 71 72 static inline int bt856_setbit(struct bt856 *encoder, u8 reg, u8 bit, u8 value) 73 { 74 return bt856_write(encoder, reg, 75 (encoder->reg[reg - BT856_REG_OFFSET] & ~(1 << bit)) | 76 (value ? (1 << bit) : 0)); 77 } 78 79 static void bt856_dump(struct bt856 *encoder) 80 { 81 int i; 82 83 v4l2_info(&encoder->sd, "register dump:\n"); 84 for (i = 0; i < BT856_NR_REG; i += 2) 85 printk(KERN_CONT " %02x", encoder->reg[i]); 86 printk(KERN_CONT "\n"); 87 } 88 89 /* ----------------------------------------------------------------------- */ 90 91 static int bt856_init(struct v4l2_subdev *sd, u32 arg) 92 { 93 struct bt856 *encoder = to_bt856(sd); 94 95 /* This is just for testing!!! */ 96 v4l2_dbg(1, debug, sd, "init\n"); 97 bt856_write(encoder, 0xdc, 0x18); 98 bt856_write(encoder, 0xda, 0); 99 bt856_write(encoder, 0xde, 0); 100 101 bt856_setbit(encoder, 0xdc, 3, 1); 102 /*bt856_setbit(encoder, 0xdc, 6, 0);*/ 103 bt856_setbit(encoder, 0xdc, 4, 1); 104 105 if (encoder->norm & V4L2_STD_NTSC) 106 bt856_setbit(encoder, 0xdc, 2, 0); 107 else 108 bt856_setbit(encoder, 0xdc, 2, 1); 109 110 bt856_setbit(encoder, 0xdc, 1, 1); 111 bt856_setbit(encoder, 0xde, 4, 0); 112 bt856_setbit(encoder, 0xde, 3, 1); 113 if (debug != 0) 114 bt856_dump(encoder); 115 return 0; 116 } 117 118 static int bt856_s_std_output(struct v4l2_subdev *sd, v4l2_std_id std) 119 { 120 struct bt856 *encoder = to_bt856(sd); 121 122 v4l2_dbg(1, debug, sd, "set norm %llx\n", (unsigned long long)std); 123 124 if (std & V4L2_STD_NTSC) { 125 bt856_setbit(encoder, 0xdc, 2, 0); 126 } else if (std & V4L2_STD_PAL) { 127 bt856_setbit(encoder, 0xdc, 2, 1); 128 bt856_setbit(encoder, 0xda, 0, 0); 129 /*bt856_setbit(encoder, 0xda, 0, 1);*/ 130 } else { 131 return -EINVAL; 132 } 133 encoder->norm = std; 134 if (debug != 0) 135 bt856_dump(encoder); 136 return 0; 137 } 138 139 static int bt856_s_routing(struct v4l2_subdev *sd, 140 u32 input, u32 output, u32 config) 141 { 142 struct bt856 *encoder = to_bt856(sd); 143 144 v4l2_dbg(1, debug, sd, "set input %d\n", input); 145 146 /* We only have video bus. 147 * input= 0: input is from bt819 148 * input= 1: input is from ZR36060 */ 149 switch (input) { 150 case 0: 151 bt856_setbit(encoder, 0xde, 4, 0); 152 bt856_setbit(encoder, 0xde, 3, 1); 153 bt856_setbit(encoder, 0xdc, 3, 1); 154 bt856_setbit(encoder, 0xdc, 6, 0); 155 break; 156 case 1: 157 bt856_setbit(encoder, 0xde, 4, 0); 158 bt856_setbit(encoder, 0xde, 3, 1); 159 bt856_setbit(encoder, 0xdc, 3, 1); 160 bt856_setbit(encoder, 0xdc, 6, 1); 161 break; 162 case 2: /* Color bar */ 163 bt856_setbit(encoder, 0xdc, 3, 0); 164 bt856_setbit(encoder, 0xde, 4, 1); 165 break; 166 default: 167 return -EINVAL; 168 } 169 170 if (debug != 0) 171 bt856_dump(encoder); 172 return 0; 173 } 174 175 /* ----------------------------------------------------------------------- */ 176 177 static const struct v4l2_subdev_core_ops bt856_core_ops = { 178 .init = bt856_init, 179 }; 180 181 static const struct v4l2_subdev_video_ops bt856_video_ops = { 182 .s_std_output = bt856_s_std_output, 183 .s_routing = bt856_s_routing, 184 }; 185 186 static const struct v4l2_subdev_ops bt856_ops = { 187 .core = &bt856_core_ops, 188 .video = &bt856_video_ops, 189 }; 190 191 /* ----------------------------------------------------------------------- */ 192 193 static int bt856_probe(struct i2c_client *client, 194 const struct i2c_device_id *id) 195 { 196 struct bt856 *encoder; 197 struct v4l2_subdev *sd; 198 199 /* Check if the adapter supports the needed features */ 200 if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_BYTE_DATA)) 201 return -ENODEV; 202 203 v4l_info(client, "chip found @ 0x%x (%s)\n", 204 client->addr << 1, client->adapter->name); 205 206 encoder = devm_kzalloc(&client->dev, sizeof(*encoder), GFP_KERNEL); 207 if (encoder == NULL) 208 return -ENOMEM; 209 sd = &encoder->sd; 210 v4l2_i2c_subdev_init(sd, client, &bt856_ops); 211 encoder->norm = V4L2_STD_NTSC; 212 213 bt856_write(encoder, 0xdc, 0x18); 214 bt856_write(encoder, 0xda, 0); 215 bt856_write(encoder, 0xde, 0); 216 217 bt856_setbit(encoder, 0xdc, 3, 1); 218 /*bt856_setbit(encoder, 0xdc, 6, 0);*/ 219 bt856_setbit(encoder, 0xdc, 4, 1); 220 221 if (encoder->norm & V4L2_STD_NTSC) 222 bt856_setbit(encoder, 0xdc, 2, 0); 223 else 224 bt856_setbit(encoder, 0xdc, 2, 1); 225 226 bt856_setbit(encoder, 0xdc, 1, 1); 227 bt856_setbit(encoder, 0xde, 4, 0); 228 bt856_setbit(encoder, 0xde, 3, 1); 229 230 if (debug != 0) 231 bt856_dump(encoder); 232 return 0; 233 } 234 235 static int bt856_remove(struct i2c_client *client) 236 { 237 struct v4l2_subdev *sd = i2c_get_clientdata(client); 238 239 v4l2_device_unregister_subdev(sd); 240 return 0; 241 } 242 243 static const struct i2c_device_id bt856_id[] = { 244 { "bt856", 0 }, 245 { } 246 }; 247 MODULE_DEVICE_TABLE(i2c, bt856_id); 248 249 static struct i2c_driver bt856_driver = { 250 .driver = { 251 .name = "bt856", 252 }, 253 .probe = bt856_probe, 254 .remove = bt856_remove, 255 .id_table = bt856_id, 256 }; 257 258 module_i2c_driver(bt856_driver); 259