aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/uio/uio.c
diff options
context:
space:
mode:
authorEric W. Biederman <ebiederm@aristanetworks.com>2010-09-14 14:38:36 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2010-10-22 13:16:43 -0400
commitc66fdab64fd791bdd49fed4f5785643251ddf586 (patch)
tree2d75b8ce0d1566f173511fc439b6f096bf30d9ca /drivers/uio/uio.c
parent91960a46c658b719c03fba80f1c60a96393bbcfd (diff)
uio: Statically allocate uio_class and use class .dev_attrs.
Instead of adding uio class attributes manually after the uio device has been created and we have sent a uevent to userspace, use the class attribute mechanism. This removes races and makes the code simpler. At the same time don't bother to dynamically allocate a struct class for uio, just declare one statically. Less code is needed and it is easier to set the class parameters.tune the class Signed-off-by: Eric W. Biederman <ebiederm@aristanetworks.com> Reviewed-by: Thomas Gleixner <tglx@linutronix.de> Signed-off-by: Hans J. Koch <hjk@linutronix.de> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/uio/uio.c')
-rw-r--r--drivers/uio/uio.c53
1 files changed, 18 insertions, 35 deletions
diff --git a/drivers/uio/uio.c b/drivers/uio/uio.c
index 3d4d65b0626f..3fe9a9da42d1 100644
--- a/drivers/uio/uio.c
+++ b/drivers/uio/uio.c
@@ -46,9 +46,6 @@ static struct cdev *uio_cdev;
46static DEFINE_IDR(uio_idr); 46static DEFINE_IDR(uio_idr);
47static const struct file_operations uio_fops; 47static const struct file_operations uio_fops;
48 48
49/* UIO class infrastructure */
50static struct class *uio_class;
51
52/* Protect idr accesses */ 49/* Protect idr accesses */
53static DEFINE_MUTEX(minor_lock); 50static DEFINE_MUTEX(minor_lock);
54 51
@@ -233,7 +230,6 @@ static ssize_t show_name(struct device *dev,
233 struct uio_device *idev = dev_get_drvdata(dev); 230 struct uio_device *idev = dev_get_drvdata(dev);
234 return sprintf(buf, "%s\n", idev->info->name); 231 return sprintf(buf, "%s\n", idev->info->name);
235} 232}
236static DEVICE_ATTR(name, S_IRUGO, show_name, NULL);
237 233
238static ssize_t show_version(struct device *dev, 234static ssize_t show_version(struct device *dev,
239 struct device_attribute *attr, char *buf) 235 struct device_attribute *attr, char *buf)
@@ -241,7 +237,6 @@ static ssize_t show_version(struct device *dev,
241 struct uio_device *idev = dev_get_drvdata(dev); 237 struct uio_device *idev = dev_get_drvdata(dev);
242 return sprintf(buf, "%s\n", idev->info->version); 238 return sprintf(buf, "%s\n", idev->info->version);
243} 239}
244static DEVICE_ATTR(version, S_IRUGO, show_version, NULL);
245 240
246static ssize_t show_event(struct device *dev, 241static ssize_t show_event(struct device *dev,
247 struct device_attribute *attr, char *buf) 242 struct device_attribute *attr, char *buf)
@@ -249,17 +244,18 @@ static ssize_t show_event(struct device *dev,
249 struct uio_device *idev = dev_get_drvdata(dev); 244 struct uio_device *idev = dev_get_drvdata(dev);
250 return sprintf(buf, "%u\n", (unsigned int)atomic_read(&idev->event)); 245 return sprintf(buf, "%u\n", (unsigned int)atomic_read(&idev->event));
251} 246}
252static DEVICE_ATTR(event, S_IRUGO, show_event, NULL);
253 247
254static struct attribute *uio_attrs[] = { 248static struct device_attribute uio_class_attributes[] = {
255 &dev_attr_name.attr, 249 __ATTR(name, S_IRUGO, show_name, NULL),
256 &dev_attr_version.attr, 250 __ATTR(version, S_IRUGO, show_version, NULL),
257 &dev_attr_event.attr, 251 __ATTR(event, S_IRUGO, show_event, NULL),
258 NULL, 252 {}
259}; 253};
260 254
261static struct attribute_group uio_attr_grp = { 255/* UIO class infrastructure */
262 .attrs = uio_attrs, 256static struct class uio_class = {
257 .name = "uio",
258 .dev_attrs = uio_class_attributes,
263}; 259};
264 260
265/* 261/*
@@ -276,10 +272,6 @@ static int uio_dev_add_attributes(struct uio_device *idev)
276 struct uio_port *port; 272 struct uio_port *port;
277 struct uio_portio *portio; 273 struct uio_portio *portio;
278 274
279 ret = sysfs_create_group(&idev->dev->kobj, &uio_attr_grp);
280 if (ret)
281 goto err_group;
282
283 for (mi = 0; mi < MAX_UIO_MAPS; mi++) { 275 for (mi = 0; mi < MAX_UIO_MAPS; mi++) {
284 mem = &idev->info->mem[mi]; 276 mem = &idev->info->mem[mi];
285 if (mem->size == 0) 277 if (mem->size == 0)
@@ -347,8 +339,6 @@ err_map:
347 kobject_put(&map->kobj); 339 kobject_put(&map->kobj);
348 } 340 }
349 kobject_put(idev->map_dir); 341 kobject_put(idev->map_dir);
350 sysfs_remove_group(&idev->dev->kobj, &uio_attr_grp);
351err_group:
352 dev_err(idev->dev, "error creating sysfs files (%d)\n", ret); 342 dev_err(idev->dev, "error creating sysfs files (%d)\n", ret);
353 return ret; 343 return ret;
354} 344}
@@ -374,8 +364,6 @@ static void uio_dev_del_attributes(struct uio_device *idev)
374 kobject_put(&port->portio->kobj); 364 kobject_put(&port->portio->kobj);
375 } 365 }
376 kobject_put(idev->portio_dir); 366 kobject_put(idev->portio_dir);
377
378 sysfs_remove_group(&idev->dev->kobj, &uio_attr_grp);
379} 367}
380 368
381static int uio_get_minor(struct uio_device *idev) 369static int uio_get_minor(struct uio_device *idev)
@@ -775,7 +763,6 @@ static void uio_major_cleanup(void)
775 763
776static int init_uio_class(void) 764static int init_uio_class(void)
777{ 765{
778 struct class *class;
779 int ret; 766 int ret;
780 767
781 /* This is the first time in here, set everything up properly */ 768 /* This is the first time in here, set everything up properly */
@@ -783,16 +770,14 @@ static int init_uio_class(void)
783 if (ret) 770 if (ret)
784 goto exit; 771 goto exit;
785 772
786 class = class_create(THIS_MODULE, "uio"); 773 ret = class_register(&uio_class);
787 if (IS_ERR(class)) { 774 if (ret) {
788 ret = IS_ERR(class); 775 printk(KERN_ERR "class_register failed for uio\n");
789 printk(KERN_ERR "class_create failed for uio\n"); 776 goto err_class_register;
790 goto err_class_create;
791 } 777 }
792 uio_class = class;
793 return 0; 778 return 0;
794 779
795err_class_create: 780err_class_register:
796 uio_major_cleanup(); 781 uio_major_cleanup();
797exit: 782exit:
798 return ret; 783 return ret;
@@ -800,9 +785,7 @@ exit:
800 785
801static void release_uio_class(void) 786static void release_uio_class(void)
802{ 787{
803 /* Ok, we cheat as we know we only have one uio_class */ 788 class_unregister(&uio_class);
804 class_destroy(uio_class);
805 uio_class = NULL;
806 uio_major_cleanup(); 789 uio_major_cleanup();
807} 790}
808 791
@@ -841,7 +824,7 @@ int __uio_register_device(struct module *owner,
841 if (ret) 824 if (ret)
842 goto err_get_minor; 825 goto err_get_minor;
843 826
844 idev->dev = device_create(uio_class, parent, 827 idev->dev = device_create(&uio_class, parent,
845 MKDEV(uio_major, idev->minor), idev, 828 MKDEV(uio_major, idev->minor), idev,
846 "uio%d", idev->minor); 829 "uio%d", idev->minor);
847 if (IS_ERR(idev->dev)) { 830 if (IS_ERR(idev->dev)) {
@@ -868,7 +851,7 @@ int __uio_register_device(struct module *owner,
868err_request_irq: 851err_request_irq:
869 uio_dev_del_attributes(idev); 852 uio_dev_del_attributes(idev);
870err_uio_dev_add_attributes: 853err_uio_dev_add_attributes:
871 device_destroy(uio_class, MKDEV(uio_major, idev->minor)); 854 device_destroy(&uio_class, MKDEV(uio_major, idev->minor));
872err_device_create: 855err_device_create:
873 uio_free_minor(idev); 856 uio_free_minor(idev);
874err_get_minor: 857err_get_minor:
@@ -899,7 +882,7 @@ void uio_unregister_device(struct uio_info *info)
899 882
900 uio_dev_del_attributes(idev); 883 uio_dev_del_attributes(idev);
901 884
902 device_destroy(uio_class, MKDEV(uio_major, idev->minor)); 885 device_destroy(&uio_class, MKDEV(uio_major, idev->minor));
903 kfree(idev); 886 kfree(idev);
904 887
905 return; 888 return;