aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/usb/stkwebcam/stk-webcam.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/media/usb/stkwebcam/stk-webcam.c')
-rw-r--r--drivers/media/usb/stkwebcam/stk-webcam.c59
1 files changed, 48 insertions, 11 deletions
diff --git a/drivers/media/usb/stkwebcam/stk-webcam.c b/drivers/media/usb/stkwebcam/stk-webcam.c
index 5d3c032d733c..4cbab085e348 100644
--- a/drivers/media/usb/stkwebcam/stk-webcam.c
+++ b/drivers/media/usb/stkwebcam/stk-webcam.c
@@ -28,6 +28,7 @@
28#include <linux/errno.h> 28#include <linux/errno.h>
29#include <linux/slab.h> 29#include <linux/slab.h>
30 30
31#include <linux/dmi.h>
31#include <linux/usb.h> 32#include <linux/usb.h>
32#include <linux/mm.h> 33#include <linux/mm.h>
33#include <linux/vmalloc.h> 34#include <linux/vmalloc.h>
@@ -38,12 +39,12 @@
38#include "stk-webcam.h" 39#include "stk-webcam.h"
39 40
40 41
41static bool hflip; 42static int hflip = -1;
42module_param(hflip, bool, 0444); 43module_param(hflip, int, 0444);
43MODULE_PARM_DESC(hflip, "Horizontal image flip (mirror). Defaults to 0"); 44MODULE_PARM_DESC(hflip, "Horizontal image flip (mirror). Defaults to 0");
44 45
45static bool vflip; 46static int vflip = -1;
46module_param(vflip, bool, 0444); 47module_param(vflip, int, 0444);
47MODULE_PARM_DESC(vflip, "Vertical image flip. Defaults to 0"); 48MODULE_PARM_DESC(vflip, "Vertical image flip. Defaults to 0");
48 49
49static int debug; 50static int debug;
@@ -62,6 +63,19 @@ static struct usb_device_id stkwebcam_table[] = {
62}; 63};
63MODULE_DEVICE_TABLE(usb, stkwebcam_table); 64MODULE_DEVICE_TABLE(usb, stkwebcam_table);
64 65
66/* The stk webcam laptop module is mounted upside down in some laptops :( */
67static const struct dmi_system_id stk_upside_down_dmi_table[] = {
68 {
69 .ident = "ASUS G1",
70 .matches = {
71 DMI_MATCH(DMI_SYS_VENDOR, "ASUSTeK Computer Inc."),
72 DMI_MATCH(DMI_PRODUCT_NAME, "G1")
73 }
74 },
75 {}
76};
77
78
65/* 79/*
66 * Basic stuff 80 * Basic stuff
67 */ 81 */
@@ -466,6 +480,7 @@ static int stk_setup_siobuf(struct stk_camera *dev, int index)
466 buf->dev = dev; 480 buf->dev = dev;
467 buf->v4lbuf.index = index; 481 buf->v4lbuf.index = index;
468 buf->v4lbuf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; 482 buf->v4lbuf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
483 buf->v4lbuf.flags = V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC;
469 buf->v4lbuf.field = V4L2_FIELD_NONE; 484 buf->v4lbuf.field = V4L2_FIELD_NONE;
470 buf->v4lbuf.memory = V4L2_MEMORY_MMAP; 485 buf->v4lbuf.memory = V4L2_MEMORY_MMAP;
471 buf->v4lbuf.m.offset = 2*index*buf->v4lbuf.length; 486 buf->v4lbuf.m.offset = 2*index*buf->v4lbuf.length;
@@ -816,10 +831,16 @@ static int stk_vidioc_g_ctrl(struct file *filp,
816 c->value = dev->vsettings.brightness; 831 c->value = dev->vsettings.brightness;
817 break; 832 break;
818 case V4L2_CID_HFLIP: 833 case V4L2_CID_HFLIP:
819 c->value = dev->vsettings.hflip; 834 if (dmi_check_system(stk_upside_down_dmi_table))
835 c->value = !dev->vsettings.hflip;
836 else
837 c->value = dev->vsettings.hflip;
820 break; 838 break;
821 case V4L2_CID_VFLIP: 839 case V4L2_CID_VFLIP:
822 c->value = dev->vsettings.vflip; 840 if (dmi_check_system(stk_upside_down_dmi_table))
841 c->value = !dev->vsettings.vflip;
842 else
843 c->value = dev->vsettings.vflip;
823 break; 844 break;
824 default: 845 default:
825 return -EINVAL; 846 return -EINVAL;
@@ -836,10 +857,16 @@ static int stk_vidioc_s_ctrl(struct file *filp,
836 dev->vsettings.brightness = c->value; 857 dev->vsettings.brightness = c->value;
837 return stk_sensor_set_brightness(dev, c->value >> 8); 858 return stk_sensor_set_brightness(dev, c->value >> 8);
838 case V4L2_CID_HFLIP: 859 case V4L2_CID_HFLIP:
839 dev->vsettings.hflip = c->value; 860 if (dmi_check_system(stk_upside_down_dmi_table))
861 dev->vsettings.hflip = !c->value;
862 else
863 dev->vsettings.hflip = c->value;
840 return 0; 864 return 0;
841 case V4L2_CID_VFLIP: 865 case V4L2_CID_VFLIP:
842 dev->vsettings.vflip = c->value; 866 if (dmi_check_system(stk_upside_down_dmi_table))
867 dev->vsettings.vflip = !c->value;
868 else
869 dev->vsettings.vflip = c->value;
843 return 0; 870 return 0;
844 default: 871 default:
845 return -EINVAL; 872 return -EINVAL;
@@ -1113,7 +1140,7 @@ static int stk_vidioc_dqbuf(struct file *filp,
1113 sbuf->v4lbuf.flags &= ~V4L2_BUF_FLAG_QUEUED; 1140 sbuf->v4lbuf.flags &= ~V4L2_BUF_FLAG_QUEUED;
1114 sbuf->v4lbuf.flags |= V4L2_BUF_FLAG_DONE; 1141 sbuf->v4lbuf.flags |= V4L2_BUF_FLAG_DONE;
1115 sbuf->v4lbuf.sequence = ++dev->sequence; 1142 sbuf->v4lbuf.sequence = ++dev->sequence;
1116 do_gettimeofday(&sbuf->v4lbuf.timestamp); 1143 v4l2_get_timestamp(&sbuf->v4lbuf.timestamp);
1117 1144
1118 *buf = sbuf->v4lbuf; 1145 *buf = sbuf->v4lbuf;
1119 return 0; 1146 return 0;
@@ -1275,8 +1302,18 @@ static int stk_camera_probe(struct usb_interface *interface,
1275 dev->interface = interface; 1302 dev->interface = interface;
1276 usb_get_intf(interface); 1303 usb_get_intf(interface);
1277 1304
1278 dev->vsettings.vflip = vflip; 1305 if (hflip != -1)
1279 dev->vsettings.hflip = hflip; 1306 dev->vsettings.hflip = hflip;
1307 else if (dmi_check_system(stk_upside_down_dmi_table))
1308 dev->vsettings.hflip = 1;
1309 else
1310 dev->vsettings.hflip = 0;
1311 if (vflip != -1)
1312 dev->vsettings.vflip = vflip;
1313 else if (dmi_check_system(stk_upside_down_dmi_table))
1314 dev->vsettings.vflip = 1;
1315 else
1316 dev->vsettings.vflip = 0;
1280 dev->n_sbufs = 0; 1317 dev->n_sbufs = 0;
1281 set_present(dev); 1318 set_present(dev);
1282 1319