Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

device-dax: fix cdev leak

If device_add() fails, cleanup the cdev. Otherwise, we leak a kobj_map()
with a stale device number.

As Jason points out, there is a small possibility that userspace has
opened and mapped the device in the time between cdev_add() and the
device_add() failure. We need a new kill_dax_dev() helper to invalidate
any established mappings.

Fixes: ba09c01d2fa8 ("dax: convert to the cdev api")
Cc: <stable@vger.kernel.org>
Reported-by: Jason Gunthorpe <jgunthorpe@obsidianresearch.com>
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Signed-off-by: Logan Gunthorpe <logang@deltatee.com>
Reviewed-by: Johannes Thumshirn <jthumshirn@suse.de>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

authored by

Dan Williams and committed by
Greg Kroah-Hartman
ed01e50a 233ed09d

+11 -4
+11 -4
drivers/dax/dax.c
··· 675 675 kfree(dax_dev); 676 676 } 677 677 678 - static void unregister_dax_dev(void *dev) 678 + static void kill_dax_dev(struct dax_dev *dax_dev) 679 679 { 680 - struct dax_dev *dax_dev = to_dax_dev(dev); 681 680 struct cdev *cdev = &dax_dev->cdev; 682 - 683 - dev_dbg(dev, "%s\n", __func__); 684 681 685 682 /* 686 683 * Note, rcu is not protecting the liveness of dax_dev, rcu is ··· 690 693 synchronize_rcu(); 691 694 unmap_mapping_range(dax_dev->inode->i_mapping, 0, 0, 1); 692 695 cdev_del(cdev); 696 + } 697 + 698 + static void unregister_dax_dev(void *dev) 699 + { 700 + struct dax_dev *dax_dev = to_dax_dev(dev); 701 + 702 + dev_dbg(dev, "%s\n", __func__); 703 + 704 + kill_dax_dev(dax_dev); 693 705 device_unregister(dev); 694 706 } 695 707 ··· 775 769 dev_set_name(dev, "dax%d.%d", dax_region->id, dax_dev->id); 776 770 rc = device_add(dev); 777 771 if (rc) { 772 + kill_dax_dev(dax_dev); 778 773 put_device(dev); 779 774 return ERR_PTR(rc); 780 775 }