diff options
author | Mauro Carvalho Chehab <mchehab@redhat.com> | 2010-03-11 10:41:56 -0500 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab@redhat.com> | 2010-05-17 23:47:03 -0400 |
commit | 945cdfa2c99e2a3f5ead11519ba11ed1df2dd5c1 (patch) | |
tree | 0a0a62bca91befd1e607ca6b138df2fd2083fea8 /drivers/media | |
parent | 8b0d2a052733d0a0e8ed59aeb8c7e6c90fdb793e (diff) |
V4L/DVB: ir: use a real device instead of a virtual class
Change the ir-sysfs approach to create irrcv0 as a device, instead of
using class_dev. Also, change the way input is registered, in order
to make its parent to be the irrcv device.
Due to this change, now the event device is created under
/sys/class/ir/irrcv class:
/sys/class/irrcv/irrcv0/
|-- current_protocol
|-- device -> ../../../1-3
|-- input9
| |-- capabilities
| | |-- abs
...
Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
Diffstat (limited to 'drivers/media')
-rw-r--r-- | drivers/media/IR/ir-keytable.c | 10 | ||||
-rw-r--r-- | drivers/media/IR/ir-sysfs.c | 78 |
2 files changed, 55 insertions, 33 deletions
diff --git a/drivers/media/IR/ir-keytable.c b/drivers/media/IR/ir-keytable.c index bfca26d51827..af1f4d7fb910 100644 --- a/drivers/media/IR/ir-keytable.c +++ b/drivers/media/IR/ir-keytable.c | |||
@@ -449,22 +449,15 @@ int ir_input_register(struct input_dev *input_dev, | |||
449 | input_dev->setkeycode = ir_setkeycode; | 449 | input_dev->setkeycode = ir_setkeycode; |
450 | input_set_drvdata(input_dev, ir_dev); | 450 | input_set_drvdata(input_dev, ir_dev); |
451 | 451 | ||
452 | rc = input_register_device(input_dev); | ||
453 | if (rc < 0) | ||
454 | goto err; | ||
455 | |||
456 | rc = ir_register_class(input_dev); | 452 | rc = ir_register_class(input_dev); |
457 | if (rc < 0) { | 453 | if (rc < 0) |
458 | input_unregister_device(input_dev); | ||
459 | goto err; | 454 | goto err; |
460 | } | ||
461 | 455 | ||
462 | return 0; | 456 | return 0; |
463 | 457 | ||
464 | err: | 458 | err: |
465 | kfree(rc_tab->scan); | 459 | kfree(rc_tab->scan); |
466 | kfree(ir_dev); | 460 | kfree(ir_dev); |
467 | input_set_drvdata(input_dev, NULL); | ||
468 | return rc; | 461 | return rc; |
469 | } | 462 | } |
470 | EXPORT_SYMBOL_GPL(ir_input_register); | 463 | EXPORT_SYMBOL_GPL(ir_input_register); |
@@ -493,7 +486,6 @@ void ir_input_unregister(struct input_dev *dev) | |||
493 | ir_unregister_class(dev); | 486 | ir_unregister_class(dev); |
494 | 487 | ||
495 | kfree(ir_dev); | 488 | kfree(ir_dev); |
496 | input_unregister_device(dev); | ||
497 | } | 489 | } |
498 | EXPORT_SYMBOL_GPL(ir_input_unregister); | 490 | EXPORT_SYMBOL_GPL(ir_input_unregister); |
499 | 491 | ||
diff --git a/drivers/media/IR/ir-sysfs.c b/drivers/media/IR/ir-sysfs.c index e14e6c486b52..59bd388be8d7 100644 --- a/drivers/media/IR/ir-sysfs.c +++ b/drivers/media/IR/ir-sysfs.c | |||
@@ -23,7 +23,15 @@ | |||
23 | static unsigned long ir_core_dev_number; | 23 | static unsigned long ir_core_dev_number; |
24 | 24 | ||
25 | /* class for /sys/class/irrcv */ | 25 | /* class for /sys/class/irrcv */ |
26 | static struct class *ir_input_class; | 26 | static char *ir_devnode(struct device *dev, mode_t *mode) |
27 | { | ||
28 | return kasprintf(GFP_KERNEL, "irrcv/%s", dev_name(dev)); | ||
29 | } | ||
30 | |||
31 | struct class ir_input_class = { | ||
32 | .name = "irrcv", | ||
33 | .devnode = ir_devnode, | ||
34 | }; | ||
27 | 35 | ||
28 | /** | 36 | /** |
29 | * show_protocol() - shows the current IR protocol | 37 | * show_protocol() - shows the current IR protocol |
@@ -129,6 +137,20 @@ static struct attribute *ir_dev_attrs[] = { | |||
129 | NULL, | 137 | NULL, |
130 | }; | 138 | }; |
131 | 139 | ||
140 | static struct attribute_group ir_dev_attr_grp = { | ||
141 | .attrs = ir_dev_attrs, | ||
142 | }; | ||
143 | |||
144 | static const struct attribute_group *ir_dev_attr_groups[] = { | ||
145 | &ir_dev_attr_grp, | ||
146 | NULL | ||
147 | }; | ||
148 | |||
149 | static struct device_type ir_dev_type = { | ||
150 | .groups = ir_dev_attr_groups, | ||
151 | }; | ||
152 | |||
153 | |||
132 | /** | 154 | /** |
133 | * ir_register_class() - creates the sysfs for /sys/class/irrcv/irrcv? | 155 | * ir_register_class() - creates the sysfs for /sys/class/irrcv/irrcv? |
134 | * @input_dev: the struct input_dev descriptor of the device | 156 | * @input_dev: the struct input_dev descriptor of the device |
@@ -138,7 +160,7 @@ static struct attribute *ir_dev_attrs[] = { | |||
138 | int ir_register_class(struct input_dev *input_dev) | 160 | int ir_register_class(struct input_dev *input_dev) |
139 | { | 161 | { |
140 | int rc; | 162 | int rc; |
141 | struct kobject *kobj; | 163 | const char *path; |
142 | 164 | ||
143 | struct ir_input_dev *ir_dev = input_get_drvdata(input_dev); | 165 | struct ir_input_dev *ir_dev = input_get_drvdata(input_dev); |
144 | int devno = find_first_zero_bit(&ir_core_dev_number, | 166 | int devno = find_first_zero_bit(&ir_core_dev_number, |
@@ -147,19 +169,31 @@ int ir_register_class(struct input_dev *input_dev) | |||
147 | if (unlikely(devno < 0)) | 169 | if (unlikely(devno < 0)) |
148 | return devno; | 170 | return devno; |
149 | 171 | ||
150 | ir_dev->attr.attrs = ir_dev_attrs; | 172 | ir_dev->dev.type = &ir_dev_type; |
151 | ir_dev->class_dev = device_create(ir_input_class, NULL, | 173 | ir_dev->dev.class = &ir_input_class; |
152 | input_dev->dev.devt, ir_dev, | 174 | ir_dev->dev.parent = input_dev->dev.parent; |
153 | "irrcv%d", devno); | 175 | dev_set_name(&ir_dev->dev, "irrcv%d", devno); |
154 | kobj = &ir_dev->class_dev->kobj; | 176 | rc = device_register(&ir_dev->dev); |
155 | 177 | if (rc) | |
156 | printk(KERN_WARNING "Creating IR device %s\n", kobject_name(kobj)); | 178 | return rc; |
157 | rc = sysfs_create_group(kobj, &ir_dev->attr); | 179 | |
158 | if (unlikely(rc < 0)) { | 180 | |
159 | device_destroy(ir_input_class, input_dev->dev.devt); | 181 | input_dev->dev.parent = &ir_dev->dev; |
160 | return -ENOMEM; | 182 | rc = input_register_device(input_dev); |
183 | if (rc < 0) { | ||
184 | device_del(&ir_dev->dev); | ||
185 | return rc; | ||
161 | } | 186 | } |
162 | 187 | ||
188 | __module_get(THIS_MODULE); | ||
189 | |||
190 | path = kobject_get_path(&input_dev->dev.kobj, GFP_KERNEL); | ||
191 | printk(KERN_INFO "%s: %s associated with sysfs %s\n", | ||
192 | dev_name(&ir_dev->dev), | ||
193 | input_dev->name ? input_dev->name : "Unspecified device", | ||
194 | path ? path : "N/A"); | ||
195 | kfree(path); | ||
196 | |||
163 | ir_dev->devno = devno; | 197 | ir_dev->devno = devno; |
164 | set_bit(devno, &ir_core_dev_number); | 198 | set_bit(devno, &ir_core_dev_number); |
165 | 199 | ||
@@ -176,16 +210,12 @@ int ir_register_class(struct input_dev *input_dev) | |||
176 | void ir_unregister_class(struct input_dev *input_dev) | 210 | void ir_unregister_class(struct input_dev *input_dev) |
177 | { | 211 | { |
178 | struct ir_input_dev *ir_dev = input_get_drvdata(input_dev); | 212 | struct ir_input_dev *ir_dev = input_get_drvdata(input_dev); |
179 | struct kobject *kobj; | ||
180 | 213 | ||
181 | clear_bit(ir_dev->devno, &ir_core_dev_number); | 214 | clear_bit(ir_dev->devno, &ir_core_dev_number); |
215 | input_unregister_device(input_dev); | ||
216 | device_del(&ir_dev->dev); | ||
182 | 217 | ||
183 | kobj = &ir_dev->class_dev->kobj; | 218 | module_put(THIS_MODULE); |
184 | |||
185 | sysfs_remove_group(kobj, &ir_dev->attr); | ||
186 | device_destroy(ir_input_class, input_dev->dev.devt); | ||
187 | |||
188 | kfree(ir_dev->attr.name); | ||
189 | } | 219 | } |
190 | 220 | ||
191 | /* | 221 | /* |
@@ -194,10 +224,10 @@ void ir_unregister_class(struct input_dev *input_dev) | |||
194 | 224 | ||
195 | static int __init ir_core_init(void) | 225 | static int __init ir_core_init(void) |
196 | { | 226 | { |
197 | ir_input_class = class_create(THIS_MODULE, "irrcv"); | 227 | int rc = class_register(&ir_input_class); |
198 | if (IS_ERR(ir_input_class)) { | 228 | if (rc) { |
199 | printk(KERN_ERR "ir_core: unable to register irrcv class\n"); | 229 | printk(KERN_ERR "ir_core: unable to register irrcv class\n"); |
200 | return PTR_ERR(ir_input_class); | 230 | return rc; |
201 | } | 231 | } |
202 | 232 | ||
203 | return 0; | 233 | return 0; |
@@ -205,7 +235,7 @@ static int __init ir_core_init(void) | |||
205 | 235 | ||
206 | static void __exit ir_core_exit(void) | 236 | static void __exit ir_core_exit(void) |
207 | { | 237 | { |
208 | class_destroy(ir_input_class); | 238 | class_unregister(&ir_input_class); |
209 | } | 239 | } |
210 | 240 | ||
211 | module_init(ir_core_init); | 241 | module_init(ir_core_init); |