There are many Link Layer Tests which needs host to generate specific traffic. This driver provides a way to do that. For root hub n there would be different sysfs nodes corresponding to each specific traffic generation case. For example: 1. To issue "Get Device descriptor" command for TD.7.06: echo 1 > /sys/devices/platform/lvstestdev.n.auto/get_dev_desc 2. To set U1 timeout to 127 for TD.7.18 echo 127 > /sys/devices/platform/lvstestdev.n.auto/u1_timeout 3. To set U2 timeout to 0 for TD.7.18 echo 0 > /sys/devices/platform/lvstestdev.n.auto/u2_timeout 4. To issue "Hot Reset" for TD.7.29 echo 1 > /sys/devices/platform/lvstestdev.n.auto/hot_reset Signed-off-by: Pratyush Anand <pratyush.anand@xxxxxx> --- .../ABI/testing/sysfs-devices-platform-lvstestdev | 32 ++++ drivers/usb/misc/Kconfig | 6 + drivers/usb/misc/Makefile | 1 + drivers/usb/misc/lvstestdev.c | 171 +++++++++++++++++++++ 4 files changed, 210 insertions(+) create mode 100644 Documentation/ABI/testing/sysfs-devices-platform-lvstestdev create mode 100644 drivers/usb/misc/lvstestdev.c diff --git a/Documentation/ABI/testing/sysfs-devices-platform-lvstestdev b/Documentation/ABI/testing/sysfs-devices-platform-lvstestdev new file mode 100644 index 0000000..49f5871 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-devices-platform-lvstestdev @@ -0,0 +1,32 @@ +Link Layer Validation Device is a standard device for testing of Super +Speed Link Layer tests. + +What: /sys/devices/platform/lvstestdev.n.auto/get_dev_desc +Date: March 2014 +Contact: Pratyush Anand <pratyush.anand@xxxxxx> +Description: + Write 1 to this node to issue "Get Device Descriptor" + for Link Layer Validation device. It is needed for TD.7.06. + +What: /sys/devices/platform/lvstestdev.n.auto/u1_timeout +Date: March 2014 +Contact: Pratyush Anand <pratyush.anand@xxxxxx> +Description: + Set "U1 timeout" for the downstream port where Link Layer + Validation device is connected. It is needed for TD.7.18, + TD.7.19, TD.7.20 and TD.7.21. + +What: /sys/devices/platform/lvstestdev.n.auto/u2_timeout +Date: March 2014 +Contact: Pratyush Anand <pratyush.anand@xxxxxx> +Description: + Set "U2 timeout" for the downstream port where Link Layer + Validation device is connected. It is needed for TD.7.18, + TD.7.19, TD.7.20 and TD.7.21. + +What: /sys/devices/platform/lvstestdev.n.auto/hot_reset +Date: March 2014 +Contact: Pratyush Anand <pratyush.anand@xxxxxx> +Description: + Write 1 to this node to issue "Reset" for Link Layer Validation + device. It is needed for TD.7.29, TD.7.31, TD.7.34 and TD.7.35. diff --git a/drivers/usb/misc/Kconfig b/drivers/usb/misc/Kconfig index a51e7d6..6ef1f81 100644 --- a/drivers/usb/misc/Kconfig +++ b/drivers/usb/misc/Kconfig @@ -235,3 +235,9 @@ config USB_HSIC_USB3503 depends on I2C help This option enables support for SMSC USB3503 HSIC to USB 2.0 Driver. + +config USB_LINK_LAYER_TEST + tristate "USB Link Layer Test driver" + help + This driver is for generating specific traffic for Super Speed Link + Layer Test Device. diff --git a/drivers/usb/misc/Makefile b/drivers/usb/misc/Makefile index 3e1bd70..6995c82 100644 --- a/drivers/usb/misc/Makefile +++ b/drivers/usb/misc/Makefile @@ -29,3 +29,4 @@ obj-$(CONFIG_USB_YUREX) += yurex.o obj-$(CONFIG_USB_HSIC_USB3503) += usb3503.o obj-$(CONFIG_USB_SISUSBVGA) += sisusbvga/ +obj-$(CONFIG_USB_LINK_LAYER_TEST) += lvstestdev.o diff --git a/drivers/usb/misc/lvstestdev.c b/drivers/usb/misc/lvstestdev.c new file mode 100644 index 0000000..58027a6 --- /dev/null +++ b/drivers/usb/misc/lvstestdev.c @@ -0,0 +1,171 @@ +/* + * drivers/usb/misc/lvstestdev.c + * + * Test pattern generation for Link Layer Validation System Tests + * + * Copyright (C) 2014 ST Microelectronics + * Pratyush Anand <pratyush.anand@xxxxxx> + * + * This file is licensed under the terms of the GNU General Public + * License version 2. This program is licensed "as is" without any + * warranty of any kind, whether express or implied. + */ + +#include <linux/init.h> +#include <linux/kernel.h> +#include <linux/module.h> +#include <linux/platform_device.h> +#include <linux/usb.h> +#include <linux/usb/ch11.h> + +static ssize_t issue_hot_reset(struct device *dev, + struct device_attribute *attr, const char *buf, size_t count) +{ + struct usb_device **pudev = dev_get_platdata(dev); + struct usb_device *udev = *pudev; + unsigned long val = simple_strtoul(buf, NULL, 10); + int ret; + + if (val != 1) + return -EINVAL; + + ret = usb_control_msg(udev->parent, usb_sndctrlpipe(udev->parent, 0), + USB_REQ_SET_FEATURE, USB_RT_PORT, USB_PORT_FEAT_RESET, + udev->portnum, NULL, 0, 1000); + if (ret < 0) { + dev_err(dev, "can't issue hot reset %d\n", ret); + return ret; + } + + return count; +} +static DEVICE_ATTR(hot_reset, S_IWUSR, NULL, issue_hot_reset); + +static ssize_t issue_u2_timeout(struct device *dev, + struct device_attribute *attr, const char *buf, size_t count) +{ + struct usb_device **pudev = dev_get_platdata(dev); + struct usb_device *udev = *pudev; + unsigned long val = simple_strtoul(buf, NULL, 10); + int ret; + + if (val != 0 && val != 0x7F) + return -EINVAL; + + ret = usb_control_msg(udev->parent, usb_sndctrlpipe(udev->parent, 0), + USB_REQ_SET_FEATURE, USB_RT_PORT, USB_PORT_FEAT_U2_TIMEOUT, + udev->portnum | (((val) & 0xff) << 8), NULL, 0, 1000); + if (ret < 0) { + dev_err(dev, "can't set u2 Timeout %d\n", ret); + return ret; + } + + return count; +} +static DEVICE_ATTR(u2_timeout, S_IWUSR, NULL, issue_u2_timeout); + +static ssize_t issue_u1_timeout(struct device *dev, + struct device_attribute *attr, const char *buf, size_t count) +{ + struct usb_device **pudev = dev_get_platdata(dev); + struct usb_device *udev = *pudev; + unsigned long val = simple_strtoul(buf, NULL, 10); + int ret; + + if (val != 0 && val != 0x7F) + return -EINVAL; + + ret = usb_control_msg(udev->parent, usb_sndctrlpipe(udev->parent, 0), + USB_REQ_SET_FEATURE, USB_RT_PORT, USB_PORT_FEAT_U1_TIMEOUT, + udev->portnum | (((val) & 0xff) << 8), NULL, 0, 1000); + if (ret < 0) { + dev_err(dev, "can't set U1 Timeout %d\n", ret); + return ret; + } + + return count; +} +static DEVICE_ATTR(u1_timeout, S_IWUSR, NULL, issue_u1_timeout); + +static ssize_t issue_get_device_descriptor(struct device *dev, + struct device_attribute *attr, const char *buf, size_t count) +{ + struct usb_device **pudev = dev_get_platdata(dev); + struct usb_device *udev = *pudev; + unsigned long val = simple_strtoul(buf, NULL, 10); + int ret; + + if (val != 1) + return -EINVAL; + + ret = usb_control_msg(udev, (PIPE_CONTROL << 30) | USB_DIR_IN, + USB_REQ_GET_DESCRIPTOR, USB_DIR_IN, USB_DT_DEVICE << 8, + 0, &udev->descriptor, sizeof(udev->descriptor), + USB_CTRL_GET_TIMEOUT); + if (ret < 0) { + dev_err(dev, "can't read device descriptor %d\n", ret); + return ret; + } + + return count; +} +static DEVICE_ATTR(get_dev_desc, S_IWUSR, NULL, issue_get_device_descriptor); + +static struct attribute *lvstestdev_attributes[] = { + &dev_attr_get_dev_desc.attr, + &dev_attr_u1_timeout.attr, + &dev_attr_u2_timeout.attr, + &dev_attr_hot_reset.attr, + NULL +}; + +static const struct attribute_group lvstestdev_attr_group = { + .attrs = lvstestdev_attributes, +}; + +static int +lvstestdev_probe(struct platform_device *pdev) +{ + struct usb_device **pudev; + int ret; + + pudev = dev_get_platdata(&pdev->dev); + if (!pudev) { + dev_err(&pdev->dev, "No udev with this device\n"); + return -EINVAL; + } + + ret = sysfs_create_group(&pdev->dev.kobj, &lvstestdev_attr_group); + + return 0; +} + +static int lvstestdev_remove(struct platform_device *pdev) +{ + sysfs_remove_group(&pdev->dev.kobj, &lvstestdev_attr_group); + + return 0; +} + +static struct platform_driver lvstestdev_driver = { + .probe = lvstestdev_probe, + .remove = lvstestdev_remove, + .driver = { + .name = "lvstestdev", + }, +}; + +static int __init lvstestdev_init(void) +{ + return platform_driver_register(&lvstestdev_driver); +} +module_init(lvstestdev_init); + +static void __exit lvstestdev_exit(void) +{ + platform_driver_unregister(&lvstestdev_driver); +} +module_exit(lvstestdev_exit); + +MODULE_DESCRIPTION("Link Layer Validation System Test Driver"); +MODULE_LICENSE("GPL"); -- 1.8.1.2 -- To unsubscribe from this list: send the line "unsubscribe linux-usb" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html