diff options
author | Dan Williams <dan.j.williams@intel.com> | 2015-05-01 13:11:27 -0400 |
---|---|---|
committer | Dan Williams <dan.j.williams@intel.com> | 2015-06-24 21:24:10 -0400 |
commit | eaf961536e1622ad21247ac8d44acd48ba65566e (patch) | |
tree | 479b1d2f81f9f8cc9abf99fa8f9b6496cbc88a25 /drivers/nvdimm/nd-core.h | |
parent | 9f53f9fa4ad1d8bddd4d14359cdabc531aedffe8 (diff) |
libnvdimm, nfit: add interleave-set state-tracking infrastructure
On platforms that have firmware support for reading/writing per-dimm
label space, a portion of the dimm may be accessible via an interleave
set PMEM mapping in addition to the dimm's BLK (block-data-window
aperture(s)) interface. A label, stored in a "configuration data
region" on the dimm, disambiguates which dimm addresses are accessed
through which exclusive interface.
Add infrastructure that allows the kernel to block modifications to a
label in the set while any member dimm is active. Note that this is
meant only for enforcing "no modifications of active labels" via the
coarse ioctl command. Adding/deleting namespaces from an active
interleave set is always possible via sysfs.
Another aspect of tracking interleave sets is tracking their integrity
when DIMMs in a set are physically re-ordered. For this purpose we
generate an "interleave-set cookie" that can be recorded in a label and
validated against the current configuration. It is the bus provider
implementation's responsibility to calculate the interleave set cookie
and attach it to a given region.
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>
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'drivers/nvdimm/nd-core.h')
-rw-r--r-- | drivers/nvdimm/nd-core.h | 10 |
1 files changed, 9 insertions, 1 deletions
diff --git a/drivers/nvdimm/nd-core.h b/drivers/nvdimm/nd-core.h index 0e9b41fd2546..6a4b2c066ee7 100644 --- a/drivers/nvdimm/nd-core.h +++ b/drivers/nvdimm/nd-core.h | |||
@@ -14,6 +14,9 @@ | |||
14 | #define __ND_CORE_H__ | 14 | #define __ND_CORE_H__ |
15 | #include <linux/libnvdimm.h> | 15 | #include <linux/libnvdimm.h> |
16 | #include <linux/device.h> | 16 | #include <linux/device.h> |
17 | #include <linux/libnvdimm.h> | ||
18 | #include <linux/sizes.h> | ||
19 | #include <linux/mutex.h> | ||
17 | 20 | ||
18 | extern struct list_head nvdimm_bus_list; | 21 | extern struct list_head nvdimm_bus_list; |
19 | extern struct mutex nvdimm_bus_list_mutex; | 22 | extern struct mutex nvdimm_bus_list_mutex; |
@@ -21,10 +24,11 @@ extern int nvdimm_major; | |||
21 | 24 | ||
22 | struct nvdimm_bus { | 25 | struct nvdimm_bus { |
23 | struct nvdimm_bus_descriptor *nd_desc; | 26 | struct nvdimm_bus_descriptor *nd_desc; |
27 | wait_queue_head_t probe_wait; | ||
24 | struct module *module; | 28 | struct module *module; |
25 | struct list_head list; | 29 | struct list_head list; |
26 | struct device dev; | 30 | struct device dev; |
27 | int id; | 31 | int id, probe_active; |
28 | struct mutex reconfig_mutex; | 32 | struct mutex reconfig_mutex; |
29 | }; | 33 | }; |
30 | 34 | ||
@@ -33,6 +37,7 @@ struct nvdimm { | |||
33 | void *provider_data; | 37 | void *provider_data; |
34 | unsigned long *dsm_mask; | 38 | unsigned long *dsm_mask; |
35 | struct device dev; | 39 | struct device dev; |
40 | atomic_t busy; | ||
36 | int id; | 41 | int id; |
37 | }; | 42 | }; |
38 | 43 | ||
@@ -42,10 +47,13 @@ bool is_nd_pmem(struct device *dev); | |||
42 | struct nvdimm_bus *walk_to_nvdimm_bus(struct device *nd_dev); | 47 | struct nvdimm_bus *walk_to_nvdimm_bus(struct device *nd_dev); |
43 | int __init nvdimm_bus_init(void); | 48 | int __init nvdimm_bus_init(void); |
44 | void nvdimm_bus_exit(void); | 49 | void nvdimm_bus_exit(void); |
50 | void nd_region_probe_success(struct nvdimm_bus *nvdimm_bus, struct device *dev); | ||
51 | void nd_region_disable(struct nvdimm_bus *nvdimm_bus, struct device *dev); | ||
45 | int nvdimm_bus_create_ndctl(struct nvdimm_bus *nvdimm_bus); | 52 | int nvdimm_bus_create_ndctl(struct nvdimm_bus *nvdimm_bus); |
46 | void nvdimm_bus_destroy_ndctl(struct nvdimm_bus *nvdimm_bus); | 53 | void nvdimm_bus_destroy_ndctl(struct nvdimm_bus *nvdimm_bus); |
47 | void nd_synchronize(void); | 54 | void nd_synchronize(void); |
48 | int nvdimm_bus_register_dimms(struct nvdimm_bus *nvdimm_bus); | 55 | int nvdimm_bus_register_dimms(struct nvdimm_bus *nvdimm_bus); |
49 | int nvdimm_bus_register_regions(struct nvdimm_bus *nvdimm_bus); | 56 | int nvdimm_bus_register_regions(struct nvdimm_bus *nvdimm_bus); |
57 | int nvdimm_bus_init_interleave_sets(struct nvdimm_bus *nvdimm_bus); | ||
50 | int nd_match_dimm(struct device *dev, void *data); | 58 | int nd_match_dimm(struct device *dev, void *data); |
51 | #endif /* __ND_CORE_H__ */ | 59 | #endif /* __ND_CORE_H__ */ |