diff mbox

[4/4] usb: gadget: f_fs: Add FUNCTIONFS_CONTROL_ONLY flag

Message ID 20180424213431.178991-1-zhangjerry@google.com (mailing list archive)
State New, archived
Headers show

Commit Message

Jerry Zhang April 24, 2018, 9:34 p.m. UTC
This flag allows users to directly specify when
they want a ffs instance to be used for handling
control requests only via the configfs control_config/
group. When the flag is set, user must set *none*
of the speed descriptor flags and provide no
speeds in the descriptor. This ensures that it
cannot be mixed up with a normal function.

Signed-off-by: Jerry Zhang <zhangjerry@google.com>
---
 drivers/usb/gadget/function/f_fs.c  | 22 +++++++++++-----------
 include/uapi/linux/usb/functionfs.h |  1 +
 2 files changed, 12 insertions(+), 11 deletions(-)
diff mbox

Patch

diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c
index 4b2cb9d93176..4ef37ed70c5d 100644
--- a/drivers/usb/gadget/function/f_fs.c
+++ b/drivers/usb/gadget/function/f_fs.c
@@ -338,11 +338,6 @@  static ssize_t ffs_ep0_write(struct file *file, const char __user *buf,
 	case FFS_READ_DESCRIPTORS:
 	case FFS_READ_STRINGS:
 		/* Copy data */
-		if (unlikely(len < 16)) {
-			ret = -EINVAL;
-			break;
-		}
-
 		data = ffs_prepare_buffer(buf, len);
 		if (IS_ERR(data)) {
 			ret = PTR_ERR(data);
@@ -2383,10 +2378,19 @@  static int __ffs_data_got_descs(struct ffs_data *ffs,
 			      FUNCTIONFS_VIRTUAL_ADDR |
 			      FUNCTIONFS_EVENTFD |
 			      FUNCTIONFS_ALL_CTRL_RECIP |
-			      FUNCTIONFS_CONFIG0_SETUP)) {
+			      FUNCTIONFS_CONFIG0_SETUP |
+			      FUNCTIONFS_CONTROL_ONLY)) {
 			ret = -ENOSYS;
 			goto error;
 		}
+		if ((bool) (flags & (FUNCTIONFS_HAS_FS_DESC |
+			      FUNCTIONFS_HAS_HS_DESC |
+			      FUNCTIONFS_HAS_SS_DESC)) ==
+		    (bool) (flags & FUNCTIONFS_CONTROL_ONLY)) {
+			pr_err("Must have at least one speed descriptor "
+					"or CONTROL_ONLY (but not both)\n");
+			goto error;
+		}
 		data += 12;
 		len  -= 12;
 		break;
@@ -2466,7 +2470,7 @@  static int __ffs_data_got_descs(struct ffs_data *ffs,
 		len -= ret;
 	}
 
-	if (raw_descs == data || len) {
+	if (len) {
 		ret = -EINVAL;
 		goto error;
 	}
@@ -3020,10 +3024,6 @@  static int _ffs_func_bind(struct usb_configuration *c,
 
 	ENTER();
 
-	/* Has descriptors only for speeds gadget does not support */
-	if (unlikely(!(full | high | super)))
-		return -ENOTSUPP;
-
 	/* Allocate a single chunk, less management later on */
 	vlabuf = kzalloc(vla_group_size(d), GFP_KERNEL);
 	if (unlikely(!vlabuf))
diff --git a/include/uapi/linux/usb/functionfs.h b/include/uapi/linux/usb/functionfs.h
index d77ee6b65328..25e55f485a6e 100644
--- a/include/uapi/linux/usb/functionfs.h
+++ b/include/uapi/linux/usb/functionfs.h
@@ -24,6 +24,7 @@  enum functionfs_flags {
 	FUNCTIONFS_EVENTFD = 32,
 	FUNCTIONFS_ALL_CTRL_RECIP = 64,
 	FUNCTIONFS_CONFIG0_SETUP = 128,
+	FUNCTIONFS_CONTROL_ONLY = 256,
 };
 
 /* Descriptor of an non-audio endpoint */