| .. | .. |
|---|
| 12 | 12 | #include <linux/init.h> |
|---|
| 13 | 13 | #include <linux/module.h> |
|---|
| 14 | 14 | #include <linux/fs.h> |
|---|
| 15 | +#include <linux/fs_context.h> |
|---|
| 15 | 16 | #include <linux/pagemap.h> |
|---|
| 16 | 17 | #include <linux/uts.h> |
|---|
| 17 | 18 | #include <linux/wait.h> |
|---|
| .. | .. |
|---|
| 20 | 21 | #include <linux/sched.h> |
|---|
| 21 | 22 | #include <linux/slab.h> |
|---|
| 22 | 23 | #include <linux/poll.h> |
|---|
| 23 | | -#include <linux/mmu_context.h> |
|---|
| 24 | +#include <linux/kthread.h> |
|---|
| 24 | 25 | #include <linux/aio.h> |
|---|
| 25 | 26 | #include <linux/uio.h> |
|---|
| 26 | 27 | #include <linux/refcount.h> |
|---|
| .. | .. |
|---|
| 228 | 229 | */ |
|---|
| 229 | 230 | |
|---|
| 230 | 231 | static const char *CHIP; |
|---|
| 232 | +static DEFINE_MUTEX(sb_mutex); /* Serialize superblock operations */ |
|---|
| 231 | 233 | |
|---|
| 232 | 234 | /*----------------------------------------------------------------------*/ |
|---|
| 233 | 235 | |
|---|
| .. | .. |
|---|
| 313 | 315 | case STATE_EP_READY: /* not configured yet */ |
|---|
| 314 | 316 | if (is_write) |
|---|
| 315 | 317 | return 0; |
|---|
| 316 | | - // FALLTHRU |
|---|
| 318 | + fallthrough; |
|---|
| 317 | 319 | case STATE_EP_UNBOUND: /* clean disconnect */ |
|---|
| 318 | 320 | break; |
|---|
| 319 | 321 | // case STATE_EP_DISABLED: /* "can't happen" */ |
|---|
| .. | .. |
|---|
| 345 | 347 | spin_unlock_irq (&epdata->dev->lock); |
|---|
| 346 | 348 | |
|---|
| 347 | 349 | if (likely (value == 0)) { |
|---|
| 348 | | - value = wait_event_interruptible (done.wait, done.done); |
|---|
| 350 | + value = wait_for_completion_interruptible(&done); |
|---|
| 349 | 351 | if (value != 0) { |
|---|
| 350 | 352 | spin_lock_irq (&epdata->dev->lock); |
|---|
| 351 | 353 | if (likely (epdata->ep != NULL)) { |
|---|
| .. | .. |
|---|
| 354 | 356 | usb_ep_dequeue (epdata->ep, epdata->req); |
|---|
| 355 | 357 | spin_unlock_irq (&epdata->dev->lock); |
|---|
| 356 | 358 | |
|---|
| 357 | | - wait_event (done.wait, done.done); |
|---|
| 359 | + wait_for_completion(&done); |
|---|
| 358 | 360 | if (epdata->status == -ECONNRESET) |
|---|
| 359 | 361 | epdata->status = -EINTR; |
|---|
| 360 | 362 | } else { |
|---|
| 361 | 363 | spin_unlock_irq (&epdata->dev->lock); |
|---|
| 362 | 364 | |
|---|
| 363 | 365 | DBG (epdata->dev, "endpoint gone\n"); |
|---|
| 366 | + wait_for_completion(&done); |
|---|
| 364 | 367 | epdata->status = -ENODEV; |
|---|
| 365 | 368 | } |
|---|
| 366 | 369 | } |
|---|
| .. | .. |
|---|
| 463 | 466 | struct kiocb *iocb = priv->iocb; |
|---|
| 464 | 467 | size_t ret; |
|---|
| 465 | 468 | |
|---|
| 466 | | - use_mm(mm); |
|---|
| 469 | + kthread_use_mm(mm); |
|---|
| 467 | 470 | ret = copy_to_iter(priv->buf, priv->actual, &priv->to); |
|---|
| 468 | | - unuse_mm(mm); |
|---|
| 471 | + kthread_unuse_mm(mm); |
|---|
| 469 | 472 | if (!ret) |
|---|
| 470 | 473 | ret = -EFAULT; |
|---|
| 471 | 474 | |
|---|
| .. | .. |
|---|
| 1085 | 1088 | case GADGETFS_DISCONNECT: |
|---|
| 1086 | 1089 | if (dev->state == STATE_DEV_SETUP) |
|---|
| 1087 | 1090 | dev->setup_abort = 1; |
|---|
| 1088 | | - // FALL THROUGH |
|---|
| 1091 | + fallthrough; |
|---|
| 1089 | 1092 | case GADGETFS_CONNECT: |
|---|
| 1090 | 1093 | dev->ev_next = 0; |
|---|
| 1091 | 1094 | break; |
|---|
| .. | .. |
|---|
| 1220 | 1223 | if (dev->state <= STATE_DEV_OPENED) |
|---|
| 1221 | 1224 | return DEFAULT_POLLMASK; |
|---|
| 1222 | 1225 | |
|---|
| 1223 | | - poll_wait(fd, &dev->wait, wait); |
|---|
| 1226 | + poll_wait(fd, &dev->wait, wait); |
|---|
| 1224 | 1227 | |
|---|
| 1225 | | - spin_lock_irq (&dev->lock); |
|---|
| 1228 | + spin_lock_irq(&dev->lock); |
|---|
| 1226 | 1229 | |
|---|
| 1227 | | - /* report fd mode change before acting on it */ |
|---|
| 1228 | | - if (dev->setup_abort) { |
|---|
| 1229 | | - dev->setup_abort = 0; |
|---|
| 1230 | | - mask = EPOLLHUP; |
|---|
| 1231 | | - goto out; |
|---|
| 1232 | | - } |
|---|
| 1230 | + /* report fd mode change before acting on it */ |
|---|
| 1231 | + if (dev->setup_abort) { |
|---|
| 1232 | + dev->setup_abort = 0; |
|---|
| 1233 | + mask = EPOLLHUP; |
|---|
| 1234 | + goto out; |
|---|
| 1235 | + } |
|---|
| 1233 | 1236 | |
|---|
| 1234 | | - if (dev->state == STATE_DEV_SETUP) { |
|---|
| 1235 | | - if (dev->setup_in || dev->setup_can_stall) |
|---|
| 1236 | | - mask = EPOLLOUT; |
|---|
| 1237 | | - } else { |
|---|
| 1238 | | - if (dev->ev_next != 0) |
|---|
| 1239 | | - mask = EPOLLIN; |
|---|
| 1240 | | - } |
|---|
| 1237 | + if (dev->state == STATE_DEV_SETUP) { |
|---|
| 1238 | + if (dev->setup_in || dev->setup_can_stall) |
|---|
| 1239 | + mask = EPOLLOUT; |
|---|
| 1240 | + } else { |
|---|
| 1241 | + if (dev->ev_next != 0) |
|---|
| 1242 | + mask = EPOLLIN; |
|---|
| 1243 | + } |
|---|
| 1241 | 1244 | out: |
|---|
| 1242 | | - spin_unlock_irq(&dev->lock); |
|---|
| 1243 | | - return mask; |
|---|
| 1245 | + spin_unlock_irq(&dev->lock); |
|---|
| 1246 | + return mask; |
|---|
| 1244 | 1247 | } |
|---|
| 1245 | 1248 | |
|---|
| 1246 | 1249 | static long dev_ioctl (struct file *fd, unsigned code, unsigned long value) |
|---|
| .. | .. |
|---|
| 1394 | 1397 | make_qualifier (dev); |
|---|
| 1395 | 1398 | break; |
|---|
| 1396 | 1399 | case USB_DT_OTHER_SPEED_CONFIG: |
|---|
| 1397 | | - // FALLTHROUGH |
|---|
| 1398 | 1400 | case USB_DT_CONFIG: |
|---|
| 1399 | 1401 | value = config_buf (dev, |
|---|
| 1400 | 1402 | w_value >> 8, |
|---|
| .. | .. |
|---|
| 1731 | 1733 | case STATE_DEV_UNCONNECTED: |
|---|
| 1732 | 1734 | next_event (dev, GADGETFS_SUSPEND); |
|---|
| 1733 | 1735 | ep0_readable (dev); |
|---|
| 1734 | | - /* FALLTHROUGH */ |
|---|
| 1736 | + fallthrough; |
|---|
| 1735 | 1737 | default: |
|---|
| 1736 | 1738 | break; |
|---|
| 1737 | 1739 | } |
|---|
| .. | .. |
|---|
| 1748 | 1750 | .suspend = gadgetfs_suspend, |
|---|
| 1749 | 1751 | |
|---|
| 1750 | 1752 | .driver = { |
|---|
| 1751 | | - .name = (char *) shortname, |
|---|
| 1753 | + .name = shortname, |
|---|
| 1752 | 1754 | }, |
|---|
| 1753 | 1755 | }; |
|---|
| 1754 | 1756 | |
|---|
| .. | .. |
|---|
| 1828 | 1830 | spin_lock_irq (&dev->lock); |
|---|
| 1829 | 1831 | value = -EINVAL; |
|---|
| 1830 | 1832 | if (dev->buf) { |
|---|
| 1833 | + spin_unlock_irq(&dev->lock); |
|---|
| 1831 | 1834 | kfree(kbuf); |
|---|
| 1832 | | - goto fail; |
|---|
| 1835 | + return value; |
|---|
| 1833 | 1836 | } |
|---|
| 1834 | 1837 | dev->buf = kbuf; |
|---|
| 1835 | 1838 | |
|---|
| .. | .. |
|---|
| 1876 | 1879 | |
|---|
| 1877 | 1880 | value = usb_gadget_probe_driver(&gadgetfs_driver); |
|---|
| 1878 | 1881 | if (value != 0) { |
|---|
| 1879 | | - kfree (dev->buf); |
|---|
| 1880 | | - dev->buf = NULL; |
|---|
| 1882 | + spin_lock_irq(&dev->lock); |
|---|
| 1883 | + goto fail; |
|---|
| 1881 | 1884 | } else { |
|---|
| 1882 | 1885 | /* at this point "good" hardware has for the first time |
|---|
| 1883 | 1886 | * let the USB the host see us. alternatively, if users |
|---|
| .. | .. |
|---|
| 1894 | 1897 | return value; |
|---|
| 1895 | 1898 | |
|---|
| 1896 | 1899 | fail: |
|---|
| 1900 | + dev->config = NULL; |
|---|
| 1901 | + dev->hs_config = NULL; |
|---|
| 1902 | + dev->dev = NULL; |
|---|
| 1897 | 1903 | spin_unlock_irq (&dev->lock); |
|---|
| 1898 | 1904 | pr_debug ("%s: %s fail %zd, %p\n", shortname, __func__, value, dev); |
|---|
| 1899 | 1905 | kfree (dev->buf); |
|---|
| .. | .. |
|---|
| 2003 | 2009 | }; |
|---|
| 2004 | 2010 | |
|---|
| 2005 | 2011 | static int |
|---|
| 2006 | | -gadgetfs_fill_super (struct super_block *sb, void *opts, int silent) |
|---|
| 2012 | +gadgetfs_fill_super (struct super_block *sb, struct fs_context *fc) |
|---|
| 2007 | 2013 | { |
|---|
| 2008 | 2014 | struct inode *inode; |
|---|
| 2009 | 2015 | struct dev_data *dev; |
|---|
| 2016 | + int rc; |
|---|
| 2010 | 2017 | |
|---|
| 2011 | | - if (the_device) |
|---|
| 2012 | | - return -ESRCH; |
|---|
| 2018 | + mutex_lock(&sb_mutex); |
|---|
| 2019 | + |
|---|
| 2020 | + if (the_device) { |
|---|
| 2021 | + rc = -ESRCH; |
|---|
| 2022 | + goto Done; |
|---|
| 2023 | + } |
|---|
| 2013 | 2024 | |
|---|
| 2014 | 2025 | CHIP = usb_get_gadget_udc_name(); |
|---|
| 2015 | | - if (!CHIP) |
|---|
| 2016 | | - return -ENODEV; |
|---|
| 2026 | + if (!CHIP) { |
|---|
| 2027 | + rc = -ENODEV; |
|---|
| 2028 | + goto Done; |
|---|
| 2029 | + } |
|---|
| 2017 | 2030 | |
|---|
| 2018 | 2031 | /* superblock */ |
|---|
| 2019 | 2032 | sb->s_blocksize = PAGE_SIZE; |
|---|
| .. | .. |
|---|
| 2050 | 2063 | * from binding to a controller. |
|---|
| 2051 | 2064 | */ |
|---|
| 2052 | 2065 | the_device = dev; |
|---|
| 2053 | | - return 0; |
|---|
| 2066 | + rc = 0; |
|---|
| 2067 | + goto Done; |
|---|
| 2054 | 2068 | |
|---|
| 2055 | | -Enomem: |
|---|
| 2069 | + Enomem: |
|---|
| 2056 | 2070 | kfree(CHIP); |
|---|
| 2057 | 2071 | CHIP = NULL; |
|---|
| 2072 | + rc = -ENOMEM; |
|---|
| 2058 | 2073 | |
|---|
| 2059 | | - return -ENOMEM; |
|---|
| 2074 | + Done: |
|---|
| 2075 | + mutex_unlock(&sb_mutex); |
|---|
| 2076 | + return rc; |
|---|
| 2060 | 2077 | } |
|---|
| 2061 | 2078 | |
|---|
| 2062 | 2079 | /* "mount -t gadgetfs path /dev/gadget" ends up here */ |
|---|
| 2063 | | -static struct dentry * |
|---|
| 2064 | | -gadgetfs_mount (struct file_system_type *t, int flags, |
|---|
| 2065 | | - const char *path, void *opts) |
|---|
| 2080 | +static int gadgetfs_get_tree(struct fs_context *fc) |
|---|
| 2066 | 2081 | { |
|---|
| 2067 | | - return mount_single (t, flags, opts, gadgetfs_fill_super); |
|---|
| 2082 | + return get_tree_single(fc, gadgetfs_fill_super); |
|---|
| 2083 | +} |
|---|
| 2084 | + |
|---|
| 2085 | +static const struct fs_context_operations gadgetfs_context_ops = { |
|---|
| 2086 | + .get_tree = gadgetfs_get_tree, |
|---|
| 2087 | +}; |
|---|
| 2088 | + |
|---|
| 2089 | +static int gadgetfs_init_fs_context(struct fs_context *fc) |
|---|
| 2090 | +{ |
|---|
| 2091 | + fc->ops = &gadgetfs_context_ops; |
|---|
| 2092 | + return 0; |
|---|
| 2068 | 2093 | } |
|---|
| 2069 | 2094 | |
|---|
| 2070 | 2095 | static void |
|---|
| 2071 | 2096 | gadgetfs_kill_sb (struct super_block *sb) |
|---|
| 2072 | 2097 | { |
|---|
| 2098 | + mutex_lock(&sb_mutex); |
|---|
| 2073 | 2099 | kill_litter_super (sb); |
|---|
| 2074 | 2100 | if (the_device) { |
|---|
| 2075 | 2101 | put_dev (the_device); |
|---|
| .. | .. |
|---|
| 2077 | 2103 | } |
|---|
| 2078 | 2104 | kfree(CHIP); |
|---|
| 2079 | 2105 | CHIP = NULL; |
|---|
| 2106 | + mutex_unlock(&sb_mutex); |
|---|
| 2080 | 2107 | } |
|---|
| 2081 | 2108 | |
|---|
| 2082 | 2109 | /*----------------------------------------------------------------------*/ |
|---|
| .. | .. |
|---|
| 2084 | 2111 | static struct file_system_type gadgetfs_type = { |
|---|
| 2085 | 2112 | .owner = THIS_MODULE, |
|---|
| 2086 | 2113 | .name = shortname, |
|---|
| 2087 | | - .mount = gadgetfs_mount, |
|---|
| 2114 | + .init_fs_context = gadgetfs_init_fs_context, |
|---|
| 2088 | 2115 | .kill_sb = gadgetfs_kill_sb, |
|---|
| 2089 | 2116 | }; |
|---|
| 2090 | 2117 | MODULE_ALIAS_FS("gadgetfs"); |
|---|