From d5bbd617a764b07c5a8006799046a0675c1e3b4a Mon Sep 17 00:00:00 2001 From: Brian Johnson Date: Thu, 2 Apr 2009 12:25:11 -0400 Subject: [PATCH] Update sysfs to use base 10 instead of base 16 values for controls Also use strict_strtoul rather then simple_strtoul and add range checking to the store methods. Signed-off-by: Brian Johnson --- sn9c20x-sysfs.c | 163 +++++++++++++++++++++++++++++++++++++------------------- 1 file changed, 109 insertions(+), 54 deletions(-) diff --git a/sn9c20x-sysfs.c b/sn9c20x-sysfs.c index 1e61744..1f0d75f 100644 --- a/sn9c20x-sysfs.c +++ b/sn9c20x-sysfs.c @@ -39,6 +39,41 @@ #include "sn9c20x.h" #include "sn9c20x-bridge.h" +#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 25) +int strict_strtoul(const char *cp, unsigned int base, unsigned long *res) +{ + char *tail; + unsigned long val; + size_t len; + + *res = 0; + len = strlen(cp); + if (len == 0) + return -EINVAL; + + val = simple_strtoul(cp, &tail, base); + if ((*tail == '\0') || + ((len == (size_t)(tail - cp) + 1) && (*tail == '\n'))) { + *res = val; + return 0; + } + + return -EINVAL; +} + +int strict_strtol(const char *cp, unsigned int base, long *res) +{ + int ret; + if (*cp == '-') { + ret = strict_strtoul(cp + 1, base, (unsigned long *)res); + if (!ret) + *res = -(*res); + } else + ret = strict_strtoul(cp, base, (unsigned long *)res); + + return ret; +} +#endif /** * @brief show_release @@ -134,16 +169,16 @@ static ssize_t show_information(struct device *class, struct device_attribute *a "\n" "%s\n" "\n" - "Brightness : 0x%02X\n" - "Contrast : 0x%02X\n" + "Brightness : %u\n" + "Contrast : %u\n" "Hue : %d\n" - "Saturation : 0x%02X\n" - "Gamma : 0x%02X\n" - "Exposure : 0x%02X\n" - "Gain : 0x%02X\n" - "Sharpness : 0x%02X\n" - "Red Balance : 0x%02X\n" - "Blue Balance : 0x%02X\n" + "Saturation : %u\n" + "Gamma : %u\n" + "Exposure : %u\n" + "Gain : %u\n" + "Sharpness : %u\n" + "Red Balance : %u\n" + "Blue Balance : %u\n" "Horizontal flip : %d\n" "Vertical flip : %d\n" "Auto-exposure : %d\n" @@ -152,16 +187,16 @@ static ssize_t show_information(struct device *class, struct device_attribute *a dev->vsettings.format.width, dev->vsettings.format.height, pixelfmt, - 0xFF & dev->vsettings.brightness, - 0xFF & dev->vsettings.contrast, + dev->vsettings.brightness, + dev->vsettings.contrast, dev->vsettings.hue, - 0xFF & dev->vsettings.colour, - 0xFF & dev->vsettings.gamma, - 0xFF & dev->vsettings.exposure, - 0xFF & dev->vsettings.gain, - 0x3F & dev->vsettings.sharpness, - 0x7F & dev->vsettings.red_gain, - 0x7F & dev->vsettings.blue_gain, + dev->vsettings.colour, + dev->vsettings.gamma, + dev->vsettings.exposure, + dev->vsettings.gain, + dev->vsettings.sharpness, + dev->vsettings.red_gain, + dev->vsettings.blue_gain, dev->vsettings.hflip, dev->vsettings.vflip, dev->vsettings.auto_exposure, @@ -209,7 +244,7 @@ static ssize_t show_gain(struct device *class, struct device_attribute *attr, ch struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.gain); + return sprintf(buf, "%u\n", dev->vsettings.gain); } /** @@ -229,13 +264,16 @@ static ssize_t store_gain(struct device *class, struct device_attribute *attr, const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 255) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_GAIN, @@ -261,7 +299,7 @@ static ssize_t show_exposure(struct device *class, struct device_attribute *attr struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.exposure); + return sprintf(buf, "%u\n", dev->vsettings.exposure); } /** @@ -281,13 +319,16 @@ static ssize_t store_exposure(struct device *class, struct device_attribute *att const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 255) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_EXPOSURE, @@ -314,7 +355,7 @@ static ssize_t show_brightness(struct device *class, struct device_attribute *at struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.brightness); + return sprintf(buf, "%u\n", dev->vsettings.brightness); } /** @@ -334,13 +375,16 @@ static ssize_t store_brightness(struct device *class, struct device_attribute *a const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 255) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_BRIGHTNESS, @@ -367,7 +411,7 @@ static ssize_t show_contrast(struct device *class, struct device_attribute *attr struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.contrast); + return sprintf(buf, "%u\n", dev->vsettings.contrast); } @@ -388,13 +432,16 @@ static ssize_t store_contrast(struct device *class, struct device_attribute *att const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 255) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_CONTRAST, @@ -425,7 +472,7 @@ static ssize_t show_saturation(struct device *class, struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.colour); + return sprintf(buf, "%u\n", dev->vsettings.colour); } @@ -450,13 +497,16 @@ static ssize_t store_saturation(struct device *class, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 255) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_SATURATION, @@ -512,13 +562,16 @@ static ssize_t store_hue(struct device *class, const char *buf, size_t count) #endif { - char *endp; - unsigned long value; + long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtol(buf, &endp, 10); + if (strict_strtol(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 180 || value < -180) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_HUE, @@ -551,7 +604,7 @@ static ssize_t show_gamma(struct device *class, struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.gamma); + return sprintf(buf, "%u\n", dev->vsettings.gamma); } @@ -575,13 +628,16 @@ static ssize_t store_gamma(struct device *class, const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value > 255) + return -EINVAL; sn9c20x_set_camera_control(dev, V4L2_CID_GAMMA, @@ -611,7 +667,7 @@ static ssize_t show_sharpness(struct device *class, struct device_attribute *att struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - return sprintf(buf, "%X\n", dev->vsettings.sharpness); + return sprintf(buf, "%u\n", dev->vsettings.sharpness); } /** @@ -631,15 +687,15 @@ static ssize_t store_sharpness(struct device *class, struct device_attribute *at const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 16); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; - if (value < 0 || value > 0x3f) + if (value > 63) return -EINVAL; sn9c20x_set_camera_control(dev, @@ -689,12 +745,12 @@ static ssize_t store_hflip(struct device *class, struct device_attribute *attr, const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 10); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; if (value != 0 && value != 1) return -EINVAL; @@ -745,12 +801,12 @@ static ssize_t store_vflip(struct class_device *class, const char *buf, size_t c static ssize_t store_vflip(struct device *class, struct device_attribute *attr, const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 10); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; if (value != 0 && value != 1) return -EINVAL; @@ -806,11 +862,10 @@ static ssize_t store_autoexposure(struct device *class, struct device_attribute struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - if (strncmp(buf, "1", 1) == 0) - value = 1; - else if (strncmp(buf, "0", 1) == 0) - value = 0; - else + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; + + if (value != 0 && value != 1) return -EINVAL; sn9c20x_set_camera_control(dev, @@ -859,12 +914,12 @@ static ssize_t store_autowhitebalance(struct class_device *class, const char *bu static ssize_t store_autowhitebalance(struct device *class, struct device_attribute *attr, const char *buf, size_t count) #endif { - char *endp; unsigned long value; struct video_device *vdev = to_video_device(class); struct usb_sn9c20x *dev = video_get_drvdata(vdev); - value = simple_strtoul(buf, &endp, 10); + if (strict_strtoul(buf, 10, &value) < 0) + return -EINVAL; if (value != 0 && value != 1) return -EINVAL; -- 2.11.4.GIT