Skip to content

Commit

Permalink
V4L/DVB (13458): go7007: subdev conversion
Browse files Browse the repository at this point in the history
Convert the go7007 driver to v4l2 subdev interface, using v4l2 i2c
subdev functions instead of i2c functions directly.  The v4l2 ioctl ops
functions call subdev ops instead of i2c commands.

Signed-off-by: Pete Eberlein <pete@sensoray.com>
Signed-off-by: Hans Verkuil <hverkuil@xs4all.nl>
Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
  • Loading branch information
Pete Eberlein authored and Mauro Carvalho Chehab committed Dec 5, 2009
1 parent 05d76f2 commit fa3c39b
Show file tree
Hide file tree
Showing 2 changed files with 47 additions and 71 deletions.
18 changes: 10 additions & 8 deletions drivers/staging/go7007/go7007-driver.c
Original file line number Diff line number Diff line change
Expand Up @@ -193,7 +193,8 @@ int go7007_reset_encoder(struct go7007 *go)
static int init_i2c_module(struct i2c_adapter *adapter, const char *type,
int id, int addr)
{
struct i2c_board_info info;
struct go7007 *go = i2c_get_adapdata(adapter);
struct v4l2_device *v4l2_dev = &go->v4l2_dev;
char *modname;

switch (id) {
Expand Down Expand Up @@ -225,14 +226,10 @@ static int init_i2c_module(struct i2c_adapter *adapter, const char *type,
modname = NULL;
break;
}
if (modname != NULL)
request_module(modname);

memset(&info, 0, sizeof(struct i2c_board_info));
info.addr = addr;
strlcpy(info.type, type, I2C_NAME_SIZE);
if (!i2c_new_device(adapter, &info))
if (v4l2_i2c_new_subdev(v4l2_dev, adapter, modname, type, addr, NULL))
return 0;

if (modname != NULL)
printk(KERN_INFO
"go7007: probing for module %s failed\n", modname);
Expand Down Expand Up @@ -262,6 +259,11 @@ int go7007_register_encoder(struct go7007 *go)
if (ret < 0)
return -1;

/* v4l2 init must happen before i2c subdevs */
ret = go7007_v4l2_init(go);
if (ret < 0)
return ret;

if (!go->i2c_adapter_online &&
go->board_info->flags & GO7007_BOARD_USE_ONBOARD_I2C) {
if (go7007_i2c_init(go) < 0)
Expand All @@ -282,7 +284,7 @@ int go7007_register_encoder(struct go7007 *go)
go->audio_enabled = 1;
go7007_snd_init(go);
}
return go7007_v4l2_init(go);
return 0;
}
EXPORT_SYMBOL(go7007_register_encoder);

Expand Down
100 changes: 37 additions & 63 deletions drivers/staging/go7007/go7007-v4l2.c
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
#include <linux/videodev2.h>
#include <media/v4l2-common.h>
#include <media/v4l2-ioctl.h>
#include <media/v4l2-subdev.h>
#include <linux/i2c.h>
#include <linux/mutex.h>
#include <linux/uaccess.h>
Expand All @@ -46,6 +47,9 @@
#define V4L2_MPEG_VIDEO_ENCODING_MPEG_4 3
#endif

#define call_all(dev, o, f, args...) \
v4l2_device_call_until_err(dev, 0, o, f, ##args)

static void deactivate_buffer(struct go7007_buffer *gobuf)
{
int i;
Expand Down Expand Up @@ -247,19 +251,23 @@ static int set_capture_size(struct go7007 *go, struct v4l2_format *fmt, int try)
go->modet_map[i] = 0;

if (go->board_info->sensor_flags & GO7007_SENSOR_SCALING) {
struct video_decoder_resolution res;
struct v4l2_format res;

if (fmt != NULL) {
res = *fmt;
} else {
res.type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
res.fmt.pix.width = width;
}

res.width = width;
if (height > sensor_height / 2) {
res.height = height / 2;
res.fmt.pix.height = height / 2;
go->encoder_v_halve = 0;
} else {
res.height = height;
res.fmt.pix.height = height;
go->encoder_v_halve = 1;
}
if (go->i2c_adapter_online)
i2c_clients_command(&go->i2c_adapter,
DECODER_SET_RESOLUTION, &res);
call_all(&go->v4l2_dev, video, s_fmt, &res);
} else {
if (width <= sensor_width / 4) {
go->encoder_h_halve = 1;
Expand Down Expand Up @@ -385,7 +393,7 @@ static int clip_to_modet_map(struct go7007 *go, int region,
}
#endif

static int mpeg_queryctrl(struct v4l2_queryctrl *ctrl)
static int mpeg_query_ctrl(struct v4l2_queryctrl *ctrl)
{
static const u32 mpeg_ctrls[] = {
V4L2_CID_MPEG_CLASS,
Expand Down Expand Up @@ -973,51 +981,35 @@ static int vidioc_queryctrl(struct file *file, void *priv,
struct v4l2_queryctrl *query)
{
struct go7007 *go = ((struct go7007_file *) priv)->go;
int id = query->id;

if (!go->i2c_adapter_online)
return -EIO;

i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYCTRL, query);
if (0 == call_all(&go->v4l2_dev, core, queryctrl, query))
return 0;

return (!query->name[0]) ? mpeg_queryctrl(query) : 0;
query->id = id;
return mpeg_query_ctrl(query);
}

static int vidioc_g_ctrl(struct file *file, void *priv,
struct v4l2_control *ctrl)
{
struct go7007 *go = ((struct go7007_file *) priv)->go;
struct v4l2_queryctrl query;

if (!go->i2c_adapter_online)
return -EIO;

memset(&query, 0, sizeof(query));
query.id = ctrl->id;
i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYCTRL, &query);
if (query.name[0] == 0)
return mpeg_g_ctrl(ctrl, go);
i2c_clients_command(&go->i2c_adapter, VIDIOC_G_CTRL, ctrl);
if (0 == call_all(&go->v4l2_dev, core, g_ctrl, ctrl))
return 0;

return 0;
return mpeg_g_ctrl(ctrl, go);
}

static int vidioc_s_ctrl(struct file *file, void *priv,
struct v4l2_control *ctrl)
{
struct go7007 *go = ((struct go7007_file *) priv)->go;
struct v4l2_queryctrl query;

if (!go->i2c_adapter_online)
return -EIO;

memset(&query, 0, sizeof(query));
query.id = ctrl->id;
i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYCTRL, &query);
if (query.name[0] == 0)
return mpeg_s_ctrl(ctrl, go);
i2c_clients_command(&go->i2c_adapter, VIDIOC_S_CTRL, ctrl);
if (0 == call_all(&go->v4l2_dev, core, s_ctrl, ctrl))
return 0;

return 0;
return mpeg_s_ctrl(ctrl, go);
}

static int vidioc_g_parm(struct file *filp, void *priv,
Expand Down Expand Up @@ -1135,8 +1127,7 @@ static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *std)
if (go->streaming)
return -EBUSY;

if (!(go->board_info->sensor_flags & GO7007_SENSOR_TV) &&
*std != 0)
if (!(go->board_info->sensor_flags & GO7007_SENSOR_TV) && *std != 0)
return -EINVAL;

if (*std == 0)
Expand All @@ -1146,9 +1137,7 @@ static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *std)
go->input == go->board_info->num_inputs - 1) {
if (!go->i2c_adapter_online)
return -EIO;
i2c_clients_command(&go->i2c_adapter,
VIDIOC_S_STD, std);
if (!*std) /* hack to indicate EINVAL from tuner */
if (call_all(&go->v4l2_dev, core, s_std, *std) < 0)
return -EINVAL;
}

Expand All @@ -1164,9 +1153,7 @@ static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *std)
} else
return -EINVAL;

if (go->i2c_adapter_online)
i2c_clients_command(&go->i2c_adapter,
VIDIOC_S_STD, std);
call_all(&go->v4l2_dev, core, s_std, *std);
set_capture_size(go, NULL, 0);

return 0;
Expand All @@ -1180,7 +1167,7 @@ static int vidioc_querystd(struct file *file, void *priv, v4l2_std_id *std)
go->input == go->board_info->num_inputs - 1) {
if (!go->i2c_adapter_online)
return -EIO;
i2c_clients_command(&go->i2c_adapter, VIDIOC_QUERYSTD, std);
return call_all(&go->v4l2_dev, video, querystd, std);
} else if (go->board_info->sensor_flags & GO7007_SENSOR_TV)
*std = V4L2_STD_NTSC | V4L2_STD_PAL | V4L2_STD_SECAM;
else
Expand Down Expand Up @@ -1238,14 +1225,8 @@ static int vidioc_s_input(struct file *file, void *priv, unsigned int input)
return -EBUSY;

go->input = input;
if (go->i2c_adapter_online) {
i2c_clients_command(&go->i2c_adapter, VIDIOC_S_INPUT,
&go->board_info->inputs[input].video_input);
i2c_clients_command(&go->i2c_adapter, VIDIOC_S_AUDIO,
&go->board_info->inputs[input].audio_input);
}

return 0;
return call_all(&go->v4l2_dev, video, s_routing, input, 0, 0);
}

static int vidioc_g_tuner(struct file *file, void *priv,
Expand All @@ -1260,10 +1241,7 @@ static int vidioc_g_tuner(struct file *file, void *priv,
if (!go->i2c_adapter_online)
return -EIO;

i2c_clients_command(&go->i2c_adapter, VIDIOC_G_TUNER, t);

t->index = 0;
return 0;
return call_all(&go->v4l2_dev, tuner, g_tuner, t);
}

static int vidioc_s_tuner(struct file *file, void *priv,
Expand All @@ -1287,9 +1265,7 @@ static int vidioc_s_tuner(struct file *file, void *priv,
break;
}

i2c_clients_command(&go->i2c_adapter, VIDIOC_S_TUNER, t);

return 0;
return call_all(&go->v4l2_dev, tuner, s_tuner, t);
}

static int vidioc_g_frequency(struct file *file, void *priv,
Expand All @@ -1303,8 +1279,8 @@ static int vidioc_g_frequency(struct file *file, void *priv,
return -EIO;

f->type = V4L2_TUNER_ANALOG_TV;
i2c_clients_command(&go->i2c_adapter, VIDIOC_G_FREQUENCY, f);
return 0;

return call_all(&go->v4l2_dev, tuner, g_frequency, f);
}

static int vidioc_s_frequency(struct file *file, void *priv,
Expand All @@ -1317,9 +1293,7 @@ static int vidioc_s_frequency(struct file *file, void *priv,
if (!go->i2c_adapter_online)
return -EIO;

i2c_clients_command(&go->i2c_adapter, VIDIOC_S_FREQUENCY, f);

return 0;
return call_all(&go->v4l2_dev, tuner, s_frequency, f);
}

static int vidioc_cropcap(struct file *file, void *priv,
Expand Down

0 comments on commit fa3c39b

Please sign in to comment.