diff options
author | Dan Williams <dan.j.williams@intel.com> | 2015-04-25 03:56:17 -0400 |
---|---|---|
committer | Dan Williams <dan.j.williams@intel.com> | 2015-06-24 21:24:10 -0400 |
commit | e6dfb2de47768efe8cc37c9a1863d2aff81440fb (patch) | |
tree | a1ad89328d88a37195f23ca9421071fc29e6722f /drivers/nvdimm/core.c | |
parent | 45def22c1fab85764646746ce38d45b2f3281fa5 (diff) |
libnvdimm, nfit: dimm/memory-devices
Enable nvdimm devices to be registered on a nvdimm_bus. The kernel
assigned device id for nvdimm devicesis dynamic. If userspace needs a
more static identifier it should consult a provider-specific attribute.
In the case where NFIT is the provider, the 'nmemX/nfit/handle' or
'nmemX/nfit/serial' attributes may be used for this purpose.
Cc: Neil Brown <neilb@suse.de>
Cc: <linux-acpi@vger.kernel.org>
Cc: Greg KH <gregkh@linuxfoundation.org>
Cc: Robert Moore <robert.moore@intel.com>
Cc: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Acked-by: Christoph Hellwig <hch@lst.de>
Acked-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Tested-by: Toshi Kani <toshi.kani@hp.com>
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'drivers/nvdimm/core.c')
-rw-r--r-- | drivers/nvdimm/core.c | 33 |
1 files changed, 31 insertions, 2 deletions
diff --git a/drivers/nvdimm/core.c b/drivers/nvdimm/core.c index fa7ab5ad0318..ef957eb37c90 100644 --- a/drivers/nvdimm/core.c +++ b/drivers/nvdimm/core.c | |||
@@ -18,8 +18,8 @@ | |||
18 | #include <linux/slab.h> | 18 | #include <linux/slab.h> |
19 | #include "nd-core.h" | 19 | #include "nd-core.h" |
20 | 20 | ||
21 | static LIST_HEAD(nvdimm_bus_list); | 21 | LIST_HEAD(nvdimm_bus_list); |
22 | static DEFINE_MUTEX(nvdimm_bus_list_mutex); | 22 | DEFINE_MUTEX(nvdimm_bus_list_mutex); |
23 | static DEFINE_IDA(nd_ida); | 23 | static DEFINE_IDA(nd_ida); |
24 | 24 | ||
25 | static void nvdimm_bus_release(struct device *dev) | 25 | static void nvdimm_bus_release(struct device *dev) |
@@ -48,6 +48,19 @@ struct nvdimm_bus_descriptor *to_nd_desc(struct nvdimm_bus *nvdimm_bus) | |||
48 | } | 48 | } |
49 | EXPORT_SYMBOL_GPL(to_nd_desc); | 49 | EXPORT_SYMBOL_GPL(to_nd_desc); |
50 | 50 | ||
51 | struct nvdimm_bus *walk_to_nvdimm_bus(struct device *nd_dev) | ||
52 | { | ||
53 | struct device *dev; | ||
54 | |||
55 | for (dev = nd_dev; dev; dev = dev->parent) | ||
56 | if (dev->release == nvdimm_bus_release) | ||
57 | break; | ||
58 | dev_WARN_ONCE(nd_dev, !dev, "invalid dev, not on nd bus\n"); | ||
59 | if (dev) | ||
60 | return to_nvdimm_bus(dev); | ||
61 | return NULL; | ||
62 | } | ||
63 | |||
51 | static const char *nvdimm_bus_provider(struct nvdimm_bus *nvdimm_bus) | 64 | static const char *nvdimm_bus_provider(struct nvdimm_bus *nvdimm_bus) |
52 | { | 65 | { |
53 | struct nvdimm_bus_descriptor *nd_desc = nvdimm_bus->nd_desc; | 66 | struct nvdimm_bus_descriptor *nd_desc = nvdimm_bus->nd_desc; |
@@ -121,6 +134,21 @@ struct nvdimm_bus *nvdimm_bus_register(struct device *parent, | |||
121 | } | 134 | } |
122 | EXPORT_SYMBOL_GPL(nvdimm_bus_register); | 135 | EXPORT_SYMBOL_GPL(nvdimm_bus_register); |
123 | 136 | ||
137 | static int child_unregister(struct device *dev, void *data) | ||
138 | { | ||
139 | /* | ||
140 | * the singular ndctl class device per bus needs to be | ||
141 | * "device_destroy"ed, so skip it here | ||
142 | * | ||
143 | * i.e. remove classless children | ||
144 | */ | ||
145 | if (dev->class) | ||
146 | /* pass */; | ||
147 | else | ||
148 | device_unregister(dev); | ||
149 | return 0; | ||
150 | } | ||
151 | |||
124 | void nvdimm_bus_unregister(struct nvdimm_bus *nvdimm_bus) | 152 | void nvdimm_bus_unregister(struct nvdimm_bus *nvdimm_bus) |
125 | { | 153 | { |
126 | if (!nvdimm_bus) | 154 | if (!nvdimm_bus) |
@@ -130,6 +158,7 @@ void nvdimm_bus_unregister(struct nvdimm_bus *nvdimm_bus) | |||
130 | list_del_init(&nvdimm_bus->list); | 158 | list_del_init(&nvdimm_bus->list); |
131 | mutex_unlock(&nvdimm_bus_list_mutex); | 159 | mutex_unlock(&nvdimm_bus_list_mutex); |
132 | 160 | ||
161 | device_for_each_child(&nvdimm_bus->dev, NULL, child_unregister); | ||
133 | nvdimm_bus_destroy_ndctl(nvdimm_bus); | 162 | nvdimm_bus_destroy_ndctl(nvdimm_bus); |
134 | 163 | ||
135 | device_unregister(&nvdimm_bus->dev); | 164 | device_unregister(&nvdimm_bus->dev); |