[PATCH v2 07/10] mt9m032: Put HFLIP and VFLIP controls in a cluster
HFLIP and VFLIP are often set together to rotate the image by 180°.
Putting the controls in a cluster makes sure they will always be applied
together, getting rid of a race condition that could result in one bad
frame.
Signed-off-by: Laurent Pinchart <laurent.pinchart@xxxxxxxxxxxxxxxx>
---
drivers/media/video/mt9m032.c | 43 +++++++++++++++++++---------------------
1 files changed, 20 insertions(+), 23 deletions(-)
diff --git a/drivers/media/video/mt9m032.c b/drivers/media/video/mt9m032.c
index cfed53a..6bd4280 100644
--- a/drivers/media/video/mt9m032.c
+++ b/drivers/media/video/mt9m032.c
@@ -107,7 +107,12 @@ struct mt9m032 {
struct v4l2_subdev subdev;
struct media_pad pad;
struct mt9m032_platform_data *pdata;
+
struct v4l2_ctrl_handler ctrls;
+ struct {
+ struct v4l2_ctrl *hflip;
+ struct v4l2_ctrl *vflip;
+ };
bool streaming;
@@ -116,8 +121,6 @@ struct mt9m032 {
struct v4l2_mbus_framefmt format; /* height and width always the same as in crop */
struct v4l2_rect crop;
struct v4l2_fract frame_interval;
-
- struct v4l2_ctrl *hflip, *vflip;
};
#define to_mt9m032(sd) container_of(sd, struct mt9m032, subdev)
@@ -503,23 +506,13 @@ static int update_read_mode2(struct mt9m032 *sensor, bool vflip, bool hflip)
{
struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
int reg_val = (!!vflip) << MT9M032_READ_MODE2_VFLIP_SHIFT
- | (!!hflip) << MT9M032_READ_MODE2_HFLIP_SHIFT
- | MT9M032_READ_MODE2_ROW_BLC
- | 0x0007;
+ | (!!hflip) << MT9M032_READ_MODE2_HFLIP_SHIFT
+ | MT9M032_READ_MODE2_ROW_BLC
+ | 0x0007;
return mt9m032_write_reg(client, MT9M032_READ_MODE2, reg_val);
}
-static int mt9m032_set_hflip(struct mt9m032 *sensor, s32 val)
-{
- return update_read_mode2(sensor, sensor->vflip->cur.val, val);
-}
-
-static int mt9m032_set_vflip(struct mt9m032 *sensor, s32 val)
-{
- return update_read_mode2(sensor, val, sensor->hflip->cur.val);
-}
-
static int mt9m032_set_exposure(struct mt9m032 *sensor, s32 val)
{
struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
@@ -581,17 +574,17 @@ static int mt9m032_try_ctrl(struct v4l2_ctrl *ctrl)
static int mt9m032_set_ctrl(struct v4l2_ctrl *ctrl)
{
- struct mt9m032 *sensor = container_of(ctrl->handler, struct mt9m032, ctrls);
+ struct mt9m032 *sensor =
+ container_of(ctrl->handler, struct mt9m032, ctrls);
switch (ctrl->id) {
case V4L2_CID_GAIN:
return mt9m032_set_gain(sensor, ctrl->val);
case V4L2_CID_HFLIP:
- return mt9m032_set_hflip(sensor, ctrl->val);
-
case V4L2_CID_VFLIP:
- return mt9m032_set_vflip(sensor, ctrl->val);
+ return update_read_mode2(sensor, sensor->vflip->val,
+ sensor->hflip->val);
case V4L2_CID_EXPOSURE:
return mt9m032_set_exposure(sensor, ctrl->val);
@@ -700,10 +693,14 @@ static int mt9m032_probe(struct i2c_client *client,
v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
V4L2_CID_GAIN, 0, 127, 1, 64);
- sensor->hflip = v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
- V4L2_CID_HFLIP, 0, 1, 1, 0);
- sensor->vflip = v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
- V4L2_CID_VFLIP, 0, 1, 1, 0);
+ sensor->hflip = v4l2_ctrl_new_std(&sensor->ctrls,
+ &mt9m032_ctrl_ops,
+ V4L2_CID_HFLIP, 0, 1, 1, 0);
+ sensor->vflip = v4l2_ctrl_new_std(&sensor->ctrls,
+ &mt9m032_ctrl_ops,
+ V4L2_CID_VFLIP, 0, 1, 1, 0);
+ v4l2_ctrl_cluster(2, &sensor->hflip);
+
v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
V4L2_CID_EXPOSURE, 0, 8000, 1, 1700); /* 1.7ms */
--
1.7.3.4
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
[Linux Input]
[Video for Linux]
[Mplayer Users]
[Linux USB Devel]
[Linux Audio Users]
[Photos]
[Yosemite Photos]
[Linux Kernel]
[Linux SCSI]
[XFree86]
[Devices]
[Yosemite Backpacking]