patch-2_6_7-vs1_9_1_12
[linux-2.6.git] / drivers / base / platform.c
1 /*
2  * platform.c - platform 'pseudo' bus for legacy devices
3  *
4  * Copyright (c) 2002-3 Patrick Mochel
5  * Copyright (c) 2002-3 Open Source Development Labs
6  * 
7  * This file is released under the GPLv2
8  *
9  * Please see Documentation/driver-model/platform.txt for more
10  * information.
11  */
12
13 #include <linux/device.h>
14 #include <linux/module.h>
15 #include <linux/init.h>
16
17 struct device platform_bus = {
18         .bus_id         = "platform",
19 };
20
21 /**
22  *      platform_device_register - add a platform-level device
23  *      @dev:   platform device we're adding
24  *
25  */
26 int platform_device_register(struct platform_device * pdev)
27 {
28         if (!pdev)
29                 return -EINVAL;
30
31         if (!pdev->dev.parent)
32                 pdev->dev.parent = &platform_bus;
33
34         pdev->dev.bus = &platform_bus_type;
35         
36         snprintf(pdev->dev.bus_id,BUS_ID_SIZE,"%s%u",pdev->name,pdev->id);
37
38         pr_debug("Registering platform device '%s'. Parent at %s\n",
39                  pdev->dev.bus_id,pdev->dev.parent->bus_id);
40         return device_register(&pdev->dev);
41 }
42
43 void platform_device_unregister(struct platform_device * pdev)
44 {
45         if (pdev)
46                 device_unregister(&pdev->dev);
47 }
48
49
50 /**
51  *      platform_match - bind platform device to platform driver.
52  *      @dev:   device.
53  *      @drv:   driver.
54  *
55  *      Platform device IDs are assumed to be encoded like this: 
56  *      "<name><instance>", where <name> is a short description of the 
57  *      type of device, like "pci" or "floppy", and <instance> is the 
58  *      enumerated instance of the device, like '0' or '42'.
59  *      Driver IDs are simply "<name>". 
60  *      So, extract the <name> from the platform_device structure, 
61  *      and compare it against the name of the driver. Return whether 
62  *      they match or not.
63  */
64
65 static int platform_match(struct device * dev, struct device_driver * drv)
66 {
67         struct platform_device *pdev = container_of(dev, struct platform_device, dev);
68
69         return (strncmp(pdev->name, drv->name, BUS_ID_SIZE) == 0);
70 }
71
72 static int platform_suspend(struct device * dev, u32 state)
73 {
74         int ret = 0;
75
76         if (dev->driver && dev->driver->suspend) {
77                 ret = dev->driver->suspend(dev, state, SUSPEND_DISABLE);
78                 if (ret == 0)
79                         ret = dev->driver->suspend(dev, state, SUSPEND_SAVE_STATE);
80                 if (ret == 0)
81                         ret = dev->driver->suspend(dev, state, SUSPEND_POWER_DOWN);
82         }
83         return ret;
84 }
85
86 static int platform_resume(struct device * dev)
87 {
88         int ret = 0;
89
90         if (dev->driver && dev->driver->resume) {
91                 ret = dev->driver->resume(dev, RESUME_POWER_ON);
92                 if (ret == 0)
93                         ret = dev->driver->resume(dev, RESUME_RESTORE_STATE);
94                 if (ret == 0)
95                         ret = dev->driver->resume(dev, RESUME_ENABLE);
96         }
97         return ret;
98 }
99
100 struct bus_type platform_bus_type = {
101         .name           = "platform",
102         .match          = platform_match,
103         .suspend        = platform_suspend,
104         .resume         = platform_resume,
105 };
106
107 int __init platform_bus_init(void)
108 {
109         device_register(&platform_bus);
110         return bus_register(&platform_bus_type);
111 }
112
113 EXPORT_SYMBOL(platform_bus);
114 EXPORT_SYMBOL(platform_bus_type);
115 EXPORT_SYMBOL(platform_device_register);
116 EXPORT_SYMBOL(platform_device_unregister);