aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorEvgeniy Polyakov <johnpol@2ka.mipt.ru>2005-08-11 05:20:07 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2005-09-08 17:41:26 -0400
commit7f772ed8df27c6941952452330c618512389c4c7 (patch)
tree6ad8320e0ee8bd2f4709176381662460ec4b1e45 /drivers
parent8949d2aa05ddf5e9a31d738568a79915970cb38e (diff)
[PATCH] w1: hotplug support.
Here is W1 hotplug in addition to netlink notifications. Signed-off-by: Evgeniy Polyakov <johnpol@2ka.mipt.ru> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/w1/w1.c90
-rw-r--r--drivers/w1/w1_int.c6
2 files changed, 82 insertions, 14 deletions
diff --git a/drivers/w1/w1.c b/drivers/w1/w1.c
index 0bbf029b1ef1..9c7777b6bbdc 100644
--- a/drivers/w1/w1.c
+++ b/drivers/w1/w1.c
@@ -125,27 +125,41 @@ static struct bin_attribute w1_slave_bin_attribute = {
125 .read = &w1_default_read_bin, 125 .read = &w1_default_read_bin,
126}; 126};
127 127
128static int w1_hotplug(struct device *dev, char **envp, int num_envp, char *buffer, int buffer_size);
128 129
129static struct bus_type w1_bus_type = { 130static struct bus_type w1_bus_type = {
130 .name = "w1", 131 .name = "w1",
131 .match = w1_master_match, 132 .match = w1_master_match,
133 .hotplug = w1_hotplug,
132}; 134};
133 135
134struct device_driver w1_driver = { 136struct device_driver w1_master_driver = {
135 .name = "w1_driver", 137 .name = "w1_master_driver",
136 .bus = &w1_bus_type, 138 .bus = &w1_bus_type,
137 .probe = w1_master_probe, 139 .probe = w1_master_probe,
138 .remove = w1_master_remove, 140 .remove = w1_master_remove,
139}; 141};
140 142
141struct device w1_device = { 143struct device w1_master_device = {
142 .parent = NULL, 144 .parent = NULL,
143 .bus = &w1_bus_type, 145 .bus = &w1_bus_type,
144 .bus_id = "w1 bus master", 146 .bus_id = "w1 bus master",
145 .driver = &w1_driver, 147 .driver = &w1_master_driver,
146 .release = &w1_master_release 148 .release = &w1_master_release
147}; 149};
148 150
151struct device_driver w1_slave_driver = {
152 .name = "w1_slave_driver",
153 .bus = &w1_bus_type,
154};
155
156struct device w1_slave_device = {
157 .parent = NULL,
158 .bus = &w1_bus_type,
159 .bus_id = "w1 bus slave",
160 .driver = &w1_slave_driver,
161};
162
149static ssize_t w1_master_attribute_show_name(struct device *dev, struct device_attribute *attr, char *buf) 163static ssize_t w1_master_attribute_show_name(struct device *dev, struct device_attribute *attr, char *buf)
150{ 164{
151 struct w1_master *md = container_of(dev, struct w1_master, dev); 165 struct w1_master *md = container_of(dev, struct w1_master, dev);
@@ -329,12 +343,55 @@ void w1_destroy_master_attributes(struct w1_master *master)
329 sysfs_remove_group(&master->dev.kobj, &w1_master_defattr_group); 343 sysfs_remove_group(&master->dev.kobj, &w1_master_defattr_group);
330} 344}
331 345
346#ifdef CONFIG_HOTPLUG
347static int w1_hotplug(struct device *dev, char **envp, int num_envp, char *buffer, int buffer_size)
348{
349 struct w1_master *md = NULL;
350 struct w1_slave *sl = NULL;
351 char *event_owner, *name;
352 int err, cur_index=0, cur_len=0;
353
354 if (dev->driver == &w1_master_driver) {
355 md = container_of(dev, struct w1_master, dev);
356 event_owner = "master";
357 name = md->name;
358 } else if (dev->driver == &w1_slave_driver) {
359 sl = container_of(dev, struct w1_slave, dev);
360 event_owner = "slave";
361 name = sl->name;
362 } else {
363 dev_dbg(dev, "Unknown hotplug event.\n");
364 return -EINVAL;
365 }
366
367 dev_dbg(dev, "Hotplug event for %s %s, bus_id=%s.\n", event_owner, name, dev->bus_id);
368
369 if (dev->driver != &w1_slave_driver || !sl)
370 return 0;
371
372 err = add_hotplug_env_var(envp, num_envp, &cur_index, buffer, buffer_size, &cur_len, "W1_FID=%02X", sl->reg_num.family);
373 if (err)
374 return err;
375
376 err = add_hotplug_env_var(envp, num_envp, &cur_index, buffer, buffer_size, &cur_len, "W1_SLAVE_ID=%024llX", sl->reg_num.id);
377 if (err)
378 return err;
379
380 return 0;
381};
382#else
383static int w1_hotplug(struct device *dev, char **envp, int num_envp, char *buffer, int buffer_size)
384{
385 return 0;
386}
387#endif
388
332static int __w1_attach_slave_device(struct w1_slave *sl) 389static int __w1_attach_slave_device(struct w1_slave *sl)
333{ 390{
334 int err; 391 int err;
335 392
336 sl->dev.parent = &sl->master->dev; 393 sl->dev.parent = &sl->master->dev;
337 sl->dev.driver = sl->master->driver; 394 sl->dev.driver = &w1_slave_driver;
338 sl->dev.bus = &w1_bus_type; 395 sl->dev.bus = &w1_bus_type;
339 sl->dev.release = &w1_slave_release; 396 sl->dev.release = &w1_slave_release;
340 397
@@ -507,7 +564,6 @@ void w1_reconnect_slaves(struct w1_family *f)
507 spin_unlock_bh(&w1_mlock); 564 spin_unlock_bh(&w1_mlock);
508} 565}
509 566
510
511static void w1_slave_found(unsigned long data, u64 rn) 567static void w1_slave_found(unsigned long data, u64 rn)
512{ 568{
513 int slave_count; 569 int slave_count;
@@ -783,7 +839,7 @@ static int w1_init(void)
783 goto err_out_exit_init; 839 goto err_out_exit_init;
784 } 840 }
785 841
786 retval = driver_register(&w1_driver); 842 retval = driver_register(&w1_master_driver);
787 if (retval) { 843 if (retval) {
788 printk(KERN_ERR 844 printk(KERN_ERR
789 "Failed to register master driver. err=%d.\n", 845 "Failed to register master driver. err=%d.\n",
@@ -791,18 +847,29 @@ static int w1_init(void)
791 goto err_out_bus_unregister; 847 goto err_out_bus_unregister;
792 } 848 }
793 849
850 retval = driver_register(&w1_slave_driver);
851 if (retval) {
852 printk(KERN_ERR
853 "Failed to register master driver. err=%d.\n",
854 retval);
855 goto err_out_master_unregister;
856 }
857
794 control_thread = kernel_thread(&w1_control, NULL, 0); 858 control_thread = kernel_thread(&w1_control, NULL, 0);
795 if (control_thread < 0) { 859 if (control_thread < 0) {
796 printk(KERN_ERR "Failed to create control thread. err=%d\n", 860 printk(KERN_ERR "Failed to create control thread. err=%d\n",
797 control_thread); 861 control_thread);
798 retval = control_thread; 862 retval = control_thread;
799 goto err_out_driver_unregister; 863 goto err_out_slave_unregister;
800 } 864 }
801 865
802 return 0; 866 return 0;
803 867
804err_out_driver_unregister: 868err_out_slave_unregister:
805 driver_unregister(&w1_driver); 869 driver_unregister(&w1_slave_driver);
870
871err_out_master_unregister:
872 driver_unregister(&w1_master_driver);
806 873
807err_out_bus_unregister: 874err_out_bus_unregister:
808 bus_unregister(&w1_bus_type); 875 bus_unregister(&w1_bus_type);
@@ -821,7 +888,8 @@ static void w1_fini(void)
821 control_needs_exit = 1; 888 control_needs_exit = 1;
822 wait_for_completion(&w1_control_complete); 889 wait_for_completion(&w1_control_complete);
823 890
824 driver_unregister(&w1_driver); 891 driver_unregister(&w1_slave_driver);
892 driver_unregister(&w1_master_driver);
825 bus_unregister(&w1_bus_type); 893 bus_unregister(&w1_bus_type);
826} 894}
827 895
diff --git a/drivers/w1/w1_int.c b/drivers/w1/w1_int.c
index 2a538d012194..c13724fd0971 100644
--- a/drivers/w1/w1_int.c
+++ b/drivers/w1/w1_int.c
@@ -29,9 +29,9 @@
29 29
30static u32 w1_ids = 1; 30static u32 w1_ids = 1;
31 31
32extern struct device_driver w1_driver; 32extern struct device_driver w1_master_driver;
33extern struct bus_type w1_bus_type; 33extern struct bus_type w1_bus_type;
34extern struct device w1_device; 34extern struct device w1_master_device;
35extern int w1_max_slave_count; 35extern int w1_max_slave_count;
36extern int w1_max_slave_ttl; 36extern int w1_max_slave_ttl;
37extern struct list_head w1_masters; 37extern struct list_head w1_masters;
@@ -125,7 +125,7 @@ int w1_add_master_device(struct w1_bus_master *master)
125 return(-EINVAL); 125 return(-EINVAL);
126 } 126 }
127 127
128 dev = w1_alloc_dev(w1_ids++, w1_max_slave_count, w1_max_slave_ttl, &w1_driver, &w1_device); 128 dev = w1_alloc_dev(w1_ids++, w1_max_slave_count, w1_max_slave_ttl, &w1_master_driver, &w1_master_device);
129 if (!dev) 129 if (!dev)
130 return -ENOMEM; 130 return -ENOMEM;
131 131