diff options
| -rw-r--r-- | drivers/staging/go7007/go7007-driver.c | 18 | ||||
| -rw-r--r-- | drivers/staging/go7007/go7007-v4l2.c | 100 |
2 files changed, 47 insertions, 71 deletions
diff --git a/drivers/staging/go7007/go7007-driver.c b/drivers/staging/go7007/go7007-driver.c index c5dc3b64ac03..fb1345ffb858 100644 --- a/drivers/staging/go7007/go7007-driver.c +++ b/drivers/staging/go7007/go7007-driver.c | |||
| @@ -193,7 +193,8 @@ int go7007_reset_encoder(struct go7007 *go) | |||
| 193 | static int init_i2c_module(struct i2c_adapter *adapter, const char *type, | 193 | static int init_i2c_module(struct i2c_adapter *adapter, const char *type, |
| 194 | int id, int addr) | 194 | int id, int addr) |
| 195 | { | 195 | { |
| 196 | struct i2c_board_info info; | 196 | struct go7007 *go = i2c_get_adapdata(adapter); |
| 197 | struct v4l2_device *v4l2_dev = &go->v4l2_dev; | ||
| 197 | char *modname; | 198 | char *modname; |
| 198 | 199 | ||
| 199 | switch (id) { | 200 | switch (id) { |
| @@ -225,14 +226,10 @@ static int init_i2c_module(struct i2c_adapter *adapter, const char *type, | |||
| 225 | modname = NULL; | 226 | modname = NULL; |
| 226 | break; | 227 | break; |
| 227 | } | 228 | } |
| 228 | if (modname != NULL) | ||
| 229 | request_module(modname); | ||
| 230 | 229 | ||
| 231 | memset(&info, 0, sizeof(struct i2c_board_info)); | 230 | if (v4l2_i2c_new_subdev(v4l2_dev, adapter, modname, type, addr, NULL)) |
| 232 | info.addr = addr; | ||
| 233 | strlcpy(info.type, type, I2C_NAME_SIZE); | ||
| 234 | if (!i2c_new_device(adapter, &info)) | ||
| 235 | return 0; | 231 | return 0; |
| 232 | |||
| 236 | if (modname != NULL) | 233 | if (modname != NULL) |
| 237 | printk(KERN_INFO | 234 | printk(KERN_INFO |
| 238 | "go7007: probing for module %s failed\n", modname); | 235 | "go7007: probing for module %s failed\n", modname); |
| @@ -262,6 +259,11 @@ int go7007_register_encoder(struct go7007 *go) | |||
| 262 | if (ret < 0) | 259 | if (ret < 0) |
| 263 | return -1; | 260 | return -1; |
| 264 | 261 | ||
| 262 | /* v4l2 init must happen before i2c subdevs */ | ||
| 263 | ret = go7007_v4l2_init(go); | ||
| 264 | if (ret < 0) | ||
| 265 | return ret; | ||
| 266 | |||
| 265 | if (!go->i2c_adapter_online && | 267 | if (!go->i2c_adapter_online && |
| 266 | go->board_info->flags & GO7007_BOARD_USE_ONBOARD_I2C) { | 268 | go->board_info->flags & GO7007_BOARD_USE_ONBOARD_I2C) { |
| 267 | if (go7007_i2c_init(go) < 0) | 269 | if (go7007_i2c_init(go) < 0) |
| @@ -282,7 +284,7 @@ int go7007_register_encoder(struct go7007 *go) | |||
| 282 | go->audio_enabled = 1; | 284 | go->audio_enabled = 1; |
| 283 | go7007_snd_init(go); | 285 | go7007_snd_init(go); |
| 284 | } | 286 | } |
| 285 | return go7007_v4l2_init(go); | 287 | return 0; |
| 286 | } | 288 | } |
| 287 | EXPORT_SYMBOL(go7007_register_encoder); | 289 | EXPORT_SYMBOL(go7007_register_encoder); |
| 288 | 290 | ||
diff --git a/drivers/staging/go7007/go7007-v4l2.c b/drivers/staging/go7007/go7007-v4l2.c index faa749dd0356..b18d8e2d4c5e 100644 --- a/drivers/staging/go7007/go7007-v4l2.c +++ b/drivers/staging/go7007/go7007-v4l2.c | |||
| @@ -29,6 +29,7 @@ | |||
| 29 | #include <linux/videodev2.h> | 29 | #include <linux/videodev2.h> |
| 30 | #include <media/v4l2-common.h> | 30 | #include <media/v4l2-common.h> |
| 31 | #include <media/v4l2-ioctl.h> | 31 | #include <media/v4l2-ioctl.h> |
| 32 | #include <media/v4l2-subdev.h> | ||
| 32 | #include <linux/i2c.h> | 33 | #include <linux/i2c.h> |
| 33 | #include <linux/mutex.h> | 34 | #include <linux/mutex.h> |
| 34 | #include <linux/uaccess.h> | 35 | #include <linux/uaccess.h> |
| @@ -46,6 +47,9 @@ | |||
| 46 | #define V4L2_MPEG_VIDEO_ENCODING_MPEG_4 3 | 47 | #define V4L2_MPEG_VIDEO_ENCODING_MPEG_4 3 |
| 47 | #endif | 48 | #endif |
| 48 | 49 | ||
| 50 | #define call_all(dev, o, f, args...) \ | ||
| 51 | v4l2_device_call_until_err(dev, 0, o, f, ##args) | ||
| 52 | |||
| 49 | static void deactivate_buffer(struct go7007_buffer *gobuf) | 53 | static void deactivate_buffer(struct go7007_buffer *gobuf) |
| 50 | { | 54 | { |
| 51 | int i; | 55 | int i; |
| @@ -247,19 +251,23 @@ static int set_capture_size(struct go7007 *go, struct v4l2_format *fmt, int try) | |||
| 247 | go->modet_map[i] = 0; | 251 | go->modet_map[i] = 0; |
| 248 | 252 | ||
| 249 | if (go->board_info->sensor_flags & GO7007_SENSOR_SCALING) { | 253 | if (go->board_info->sensor_flags & GO7007_SENSOR_SCALING) { |
| 250 | struct video_decoder_resolution res; | 254 | struct v4l2_format res; |
| 255 | |||
| 256 | if (fmt != NULL) { | ||
| 257 | res = *fmt; | ||
| 258 | } else { | ||
| 259 | res.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; | ||
| 260 | res.fmt.pix.width = width; | ||
| 261 | } | ||
| 251 | 262 | ||
| 252 | res.width = width; | ||
| 253 | if (height > sensor_height / 2) { | 263 | if (height > sensor_height / 2) { |
| 254 | res.height = height / 2; | 264 | res.fmt.pix.height = height / 2; |
| 255 | go->encoder_v_halve = 0; | 265 | go->encoder_v_halve = 0; |
| 256 | } else { | 266 | } else { |
| 257 | res.height = height; | 267 | res.fmt.pix.height = height; |
| 258 | go->encoder_v_halve = 1; | 268 | go->encoder_v_halve = 1; |
| 259 | } | 269 | } |
| 260 | if (go->i2c_adapter_online) | 270 | call_all(&go->v4l2_dev, video, s_fmt, &res); |
| 261 | i2c_clients_command(&go->i2c_adapter, | ||
| 262 | DECODER_SET_RESOLUTION, &res); | ||
| 263 | } else { | 271 | } else { |
| 264 | if (width <= sensor_width / 4) { | 272 | if (width <= sensor_width / 4) { |
| 265 | go->encoder_h_halve = 1; | 273 | go->encoder_h_halve = 1; |
| @@ -385,7 +393,7 @@ static int clip_to_modet_map(struct go7007 *go, int region, | |||
| 385 | } | 393 | } |
| 386 | #endif | 394 | #endif |
| 387 | 395 | ||
| 388 | static int mpeg_queryctrl(struct v4l2_queryctrl *ctrl) | 396 | static int mpeg_query_ctrl(struct v4l2_queryctrl *ctrl) |
| 389 | { | 397 | { |
| 390 | static const u32 mpeg_ctrls[] = { | 398 | static const u32 mpeg_ctrls[] = { |
| 391 | V4L2_CID_MPEG_CLASS, | 399 | V4L2_CID_MPEG_CLASS, |
| @@ -973,51 +981,35 @@ static int vidioc_queryctrl(struct file *file, void *priv, | |||
| 973 | struct v4l2_queryctrl *query) | 981 | struct v4l2_queryctrl *query) |
| 974 | { | 982 | { |
| 975 | struct go7007 *go = ((struct go7007_file *) priv)->go; | 983 | struct go7007 *go = ((struct go7007_file *) priv)->go; |
| 984 | int id = query->id; | ||
| 976 | 985 | ||
| 977 | if (!go->i2c_adapter_online) | 986 | if (0 == call_all(&go->v4l2_dev, core, queryctrl, query)) |
| 978 | return -EIO; | 987 | return 0; |
| 979 | |||
| 980 | i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYCTRL, query); | ||
| 981 | 988 | ||
| 982 | return (!query->name[0]) ? mpeg_queryctrl(query) : 0; | 989 | query->id = id; |
| 990 | return mpeg_query_ctrl(query); | ||
| 983 | } | 991 | } |
| 984 | 992 | ||
| 985 | static int vidioc_g_ctrl(struct file *file, void *priv, | 993 | static int vidioc_g_ctrl(struct file *file, void *priv, |
| 986 | struct v4l2_control *ctrl) | 994 | struct v4l2_control *ctrl) |
| 987 | { | 995 | { |
| 988 | struct go7007 *go = ((struct go7007_file *) priv)->go; | 996 | struct go7007 *go = ((struct go7007_file *) priv)->go; |
| 989 | struct v4l2_queryctrl query; | ||
| 990 | |||
| 991 | if (!go->i2c_adapter_online) | ||
| 992 | return -EIO; | ||
| 993 | 997 | ||
| 994 | memset(&query, 0, sizeof(query)); | 998 | if (0 == call_all(&go->v4l2_dev, core, g_ctrl, ctrl)) |
| 995 | query.id = ctrl->id; | 999 | return 0; |
| 996 | i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYCTRL, &query); | ||
| 997 | if (query.name[0] == 0) | ||
| 998 | return mpeg_g_ctrl(ctrl, go); | ||
| 999 | i2c_clients_command(&go->i2c_adapter, VIDIOC_G_CTRL, ctrl); | ||
| 1000 | 1000 | ||
| 1001 | return 0; | 1001 | return mpeg_g_ctrl(ctrl, go); |
| 1002 | } | 1002 | } |
| 1003 | 1003 | ||
| 1004 | static int vidioc_s_ctrl(struct file *file, void *priv, | 1004 | static int vidioc_s_ctrl(struct file *file, void *priv, |
| 1005 | struct v4l2_control *ctrl) | 1005 | struct v4l2_control *ctrl) |
| 1006 | { | 1006 | { |
| 1007 | struct go7007 *go = ((struct go7007_file *) priv)->go; | 1007 | struct go7007 *go = ((struct go7007_file *) priv)->go; |
| 1008 | struct v4l2_queryctrl query; | ||
| 1009 | |||
| 1010 | if (!go->i2c_adapter_online) | ||
| 1011 | return -EIO; | ||
| 1012 | 1008 | ||
| 1013 | memset(&query, 0, sizeof(query)); | 1009 | if (0 == call_all(&go->v4l2_dev, core, s_ctrl, ctrl)) |
| 1014 | query.id = ctrl->id; | 1010 | return 0; |
| 1015 | i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYCTRL, &query); | ||
| 1016 | if (query.name[0] == 0) | ||
| 1017 | return mpeg_s_ctrl(ctrl, go); | ||
| 1018 | i2c_clients_command(&go->i2c_adapter, VIDIOC_S_CTRL, ctrl); | ||
| 1019 | 1011 | ||
| 1020 | return 0; | 1012 | return mpeg_s_ctrl(ctrl, go); |
| 1021 | } | 1013 | } |
| 1022 | 1014 | ||
| 1023 | static int vidioc_g_parm(struct file *filp, void *priv, | 1015 | static int vidioc_g_parm(struct file *filp, void *priv, |
| @@ -1135,8 +1127,7 @@ static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *std) | |||
| 1135 | if (go->streaming) | 1127 | if (go->streaming) |
| 1136 | return -EBUSY; | 1128 | return -EBUSY; |
| 1137 | 1129 | ||
| 1138 | if (!(go->board_info->sensor_flags & GO7007_SENSOR_TV) && | 1130 | if (!(go->board_info->sensor_flags & GO7007_SENSOR_TV) && *std != 0) |
| 1139 | *std != 0) | ||
| 1140 | return -EINVAL; | 1131 | return -EINVAL; |
| 1141 | 1132 | ||
| 1142 | if (*std == 0) | 1133 | if (*std == 0) |
| @@ -1146,9 +1137,7 @@ static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *std) | |||
| 1146 | go->input == go->board_info->num_inputs - 1) { | 1137 | go->input == go->board_info->num_inputs - 1) { |
| 1147 | if (!go->i2c_adapter_online) | 1138 | if (!go->i2c_adapter_online) |
| 1148 | return -EIO; | 1139 | return -EIO; |
| 1149 | i2c_clients_command(&go->i2c_adapter, | 1140 | if (call_all(&go->v4l2_dev, core, s_std, *std) < 0) |
| 1150 | VIDIOC_S_STD, std); | ||
| 1151 | if (!*std) /* hack to indicate EINVAL from tuner */ | ||
| 1152 | return -EINVAL; | 1141 | return -EINVAL; |
| 1153 | } | 1142 | } |
| 1154 | 1143 | ||
| @@ -1164,9 +1153,7 @@ static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *std) | |||
| 1164 | } else | 1153 | } else |
| 1165 | return -EINVAL; | 1154 | return -EINVAL; |
| 1166 | 1155 | ||
| 1167 | if (go->i2c_adapter_online) | 1156 | call_all(&go->v4l2_dev, core, s_std, *std); |
| 1168 | i2c_clients_command(&go->i2c_adapter, | ||
| 1169 | VIDIOC_S_STD, std); | ||
| 1170 | set_capture_size(go, NULL, 0); | 1157 | set_capture_size(go, NULL, 0); |
| 1171 | 1158 | ||
| 1172 | return 0; | 1159 | return 0; |
| @@ -1180,7 +1167,7 @@ static int vidioc_querystd(struct file *file, void *priv, v4l2_std_id *std) | |||
| 1180 | go->input == go->board_info->num_inputs - 1) { | 1167 | go->input == go->board_info->num_inputs - 1) { |
| 1181 | if (!go->i2c_adapter_online) | 1168 | if (!go->i2c_adapter_online) |
| 1182 | return -EIO; | 1169 | return -EIO; |
| 1183 | i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYSTD, std); | 1170 | return call_all(&go->v4l2_dev, video, querystd, std); |
| 1184 | } else if (go->board_info->sensor_flags & GO7007_SENSOR_TV) | 1171 | } else if (go->board_info->sensor_flags & GO7007_SENSOR_TV) |
| 1185 | *std = V4L2_STD_NTSC | V4L2_STD_PAL | V4L2_STD_SECAM; | 1172 | *std = V4L2_STD_NTSC | V4L2_STD_PAL | V4L2_STD_SECAM; |
| 1186 | else | 1173 | else |
| @@ -1238,14 +1225,8 @@ static int vidioc_s_input(struct file *file, void *priv, unsigned int input) | |||
| 1238 | return -EBUSY; | 1225 | return -EBUSY; |
| 1239 | 1226 | ||
| 1240 | go->input = input; | 1227 | go->input = input; |
| 1241 | if (go->i2c_adapter_online) { | ||
| 1242 | i2c_clients_command(&go->i2c_adapter, VIDIOC_S_INPUT, | ||
| 1243 | &go->board_info->inputs[input].video_input); | ||
| 1244 | i2c_clients_command(&go->i2c_adapter, VIDIOC_S_AUDIO, | ||
| 1245 | &go->board_info->inputs[input].audio_input); | ||
| 1246 | } | ||
| 1247 | 1228 | ||
| 1248 | return 0; | 1229 | return call_all(&go->v4l2_dev, video, s_routing, input, 0, 0); |
| 1249 | } | 1230 | } |
| 1250 | 1231 | ||
| 1251 | static int vidioc_g_tuner(struct file *file, void *priv, | 1232 | static int vidioc_g_tuner(struct file *file, void *priv, |
| @@ -1260,10 +1241,7 @@ static int vidioc_g_tuner(struct file *file, void *priv, | |||
| 1260 | if (!go->i2c_adapter_online) | 1241 | if (!go->i2c_adapter_online) |
| 1261 | return -EIO; | 1242 | return -EIO; |
| 1262 | 1243 | ||
| 1263 | i2c_clients_command(&go->i2c_adapter, VIDIOC_G_TUNER, t); | 1244 | return call_all(&go->v4l2_dev, tuner, g_tuner, t); |
| 1264 | |||
| 1265 | t->index = 0; | ||
| 1266 | return 0; | ||
| 1267 | } | 1245 | } |
| 1268 | 1246 | ||
| 1269 | static int vidioc_s_tuner(struct file *file, void *priv, | 1247 | static int vidioc_s_tuner(struct file *file, void *priv, |
| @@ -1287,9 +1265,7 @@ static int vidioc_s_tuner(struct file *file, void *priv, | |||
| 1287 | break; | 1265 | break; |
| 1288 | } | 1266 | } |
| 1289 | 1267 | ||
| 1290 | i2c_clients_command(&go->i2c_adapter, VIDIOC_S_TUNER, t); | 1268 | return call_all(&go->v4l2_dev, tuner, s_tuner, t); |
| 1291 | |||
| 1292 | return 0; | ||
| 1293 | } | 1269 | } |
| 1294 | 1270 | ||
| 1295 | static int vidioc_g_frequency(struct file *file, void *priv, | 1271 | static int vidioc_g_frequency(struct file *file, void *priv, |
| @@ -1303,8 +1279,8 @@ static int vidioc_g_frequency(struct file *file, void *priv, | |||
| 1303 | return -EIO; | 1279 | return -EIO; |
| 1304 | 1280 | ||
| 1305 | f->type = V4L2_TUNER_ANALOG_TV; | 1281 | f->type = V4L2_TUNER_ANALOG_TV; |
| 1306 | i2c_clients_command(&go->i2c_adapter, VIDIOC_G_FREQUENCY, f); | 1282 | |
| 1307 | return 0; | 1283 | return call_all(&go->v4l2_dev, tuner, g_frequency, f); |
| 1308 | } | 1284 | } |
| 1309 | 1285 | ||
| 1310 | static int vidioc_s_frequency(struct file *file, void *priv, | 1286 | static int vidioc_s_frequency(struct file *file, void *priv, |
| @@ -1317,9 +1293,7 @@ static int vidioc_s_frequency(struct file *file, void *priv, | |||
| 1317 | if (!go->i2c_adapter_online) | 1293 | if (!go->i2c_adapter_online) |
| 1318 | return -EIO; | 1294 | return -EIO; |
| 1319 | 1295 | ||
| 1320 | i2c_clients_command(&go->i2c_adapter, VIDIOC_S_FREQUENCY, f); | 1296 | return call_all(&go->v4l2_dev, tuner, s_frequency, f); |
| 1321 | |||
| 1322 | return 0; | ||
| 1323 | } | 1297 | } |
| 1324 | 1298 | ||
| 1325 | static int vidioc_cropcap(struct file *file, void *priv, | 1299 | static int vidioc_cropcap(struct file *file, void *priv, |
