lkml.org 
[lkml]   [2017]   [Mar]   [28]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH 4.10 066/111] ppdev: fix registering same device name
    Date
    4.10-stable review patch.  If anyone has any objections, please let me know.

    ------------------

    From: Sudip Mukherjee <sudipm.mukherjee@gmail.com>

    commit 9a69645dde1188723d80745c1bc6ee9af2cbe2a7 upstream.

    Usually every parallel port will have a single pardev registered with
    it. But ppdev driver is an exception. This userspace parallel port
    driver allows to create multiple parrallel port devices for a single
    parallel port. And as a result we were having a big warning like:
    "sysfs: cannot create duplicate filename '/devices/parport0/ppdev0.0'".
    And with that many parallel port printers stopped working.

    We have been using the minor number as the id field while registering
    a parralel port device with a parralel port. But when there are
    multiple parrallel port device for one single parallel port, they all
    tried to register with the same name like 'pardev0.0' and everything
    started failing.
    Use an incremented index as the id instead of the minor number.

    Fixes: 8b7d3a9d903e ("ppdev: use new parport device model")
    Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=1414656
    Bugzilla: https://bugs.archlinux.org/task/52322
    Tested-by: James Feeney <james@nurealm.net>
    Signed-off-by: Sudip Mukherjee <sudip.mukherjee@codethink.co.uk>
    Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

    ---
    drivers/char/ppdev.c | 11 +++++++++--
    1 file changed, 9 insertions(+), 2 deletions(-)

    --- a/drivers/char/ppdev.c
    +++ b/drivers/char/ppdev.c
    @@ -84,11 +84,14 @@ struct pp_struct {
    struct ieee1284_info state;
    struct ieee1284_info saved_state;
    long default_inactivity;
    + int index;
    };

    /* should we use PARDEVICE_MAX here? */
    static struct device *devices[PARPORT_MAX];

    +static DEFINE_IDA(ida_index);
    +
    /* pp_struct.flags bitfields */
    #define PP_CLAIMED (1<<0)
    #define PP_EXCL (1<<1)
    @@ -290,7 +293,7 @@ static int register_device(int minor, st
    struct pardevice *pdev = NULL;
    char *name;
    struct pardev_cb ppdev_cb;
    - int rc = 0;
    + int rc = 0, index;

    name = kasprintf(GFP_KERNEL, CHRDEV "%x", minor);
    if (name == NULL)
    @@ -303,20 +306,23 @@ static int register_device(int minor, st
    goto err;
    }

    + index = ida_simple_get(&ida_index, 0, 0, GFP_KERNEL);
    memset(&ppdev_cb, 0, sizeof(ppdev_cb));
    ppdev_cb.irq_func = pp_irq;
    ppdev_cb.flags = (pp->flags & PP_EXCL) ? PARPORT_FLAG_EXCL : 0;
    ppdev_cb.private = pp;
    - pdev = parport_register_dev_model(port, name, &ppdev_cb, minor);
    + pdev = parport_register_dev_model(port, name, &ppdev_cb, index);
    parport_put_port(port);

    if (!pdev) {
    pr_warn("%s: failed to register device!\n", name);
    rc = -ENXIO;
    + ida_simple_remove(&ida_index, index);
    goto err;
    }

    pp->pdev = pdev;
    + pp->index = index;
    dev_dbg(&pdev->dev, "registered pardevice\n");
    err:
    kfree(name);
    @@ -755,6 +761,7 @@ static int pp_release(struct inode *inod

    if (pp->pdev) {
    parport_unregister_device(pp->pdev);
    + ida_simple_remove(&ida_index, pp->index);
    pp->pdev = NULL;
    pr_debug(CHRDEV "%x: unregistered pardevice\n", minor);
    }

    \
     
     \ /
      Last update: 2017-03-28 15:21    [W:4.405 / U:0.008 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site