diff options
author | Dan Williams <dan.j.williams@intel.com> | 2016-10-05 17:04:15 -0400 |
---|---|---|
committer | Dan Williams <dan.j.williams@intel.com> | 2016-10-07 12:20:53 -0400 |
commit | 6ff3e912d32ece4e9cf8708da796e9e2e7979ffe (patch) | |
tree | 690a3f33c527aa16150ab208b535c42d97ea5cb3 /drivers/nvdimm/namespace_devs.c | |
parent | 0e3b0d123c8fd5c42f364aea3ab663b1f18dad39 (diff) |
libnvdimm, namespace: sort namespaces by dpa at init
Add more determinism to initial namespace device-name assignments by
sorting the namespaces by starting dpa.
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'drivers/nvdimm/namespace_devs.c')
-rw-r--r-- | drivers/nvdimm/namespace_devs.c | 35 |
1 files changed, 32 insertions, 3 deletions
diff --git a/drivers/nvdimm/namespace_devs.c b/drivers/nvdimm/namespace_devs.c index 47d29632b937..f0536c2789e9 100644 --- a/drivers/nvdimm/namespace_devs.c +++ b/drivers/nvdimm/namespace_devs.c | |||
@@ -12,6 +12,7 @@ | |||
12 | */ | 12 | */ |
13 | #include <linux/module.h> | 13 | #include <linux/module.h> |
14 | #include <linux/device.h> | 14 | #include <linux/device.h> |
15 | #include <linux/sort.h> | ||
15 | #include <linux/slab.h> | 16 | #include <linux/slab.h> |
16 | #include <linux/pmem.h> | 17 | #include <linux/pmem.h> |
17 | #include <linux/list.h> | 18 | #include <linux/list.h> |
@@ -66,17 +67,17 @@ static struct device_type namespace_blk_device_type = { | |||
66 | .release = namespace_blk_release, | 67 | .release = namespace_blk_release, |
67 | }; | 68 | }; |
68 | 69 | ||
69 | static bool is_namespace_pmem(struct device *dev) | 70 | static bool is_namespace_pmem(const struct device *dev) |
70 | { | 71 | { |
71 | return dev ? dev->type == &namespace_pmem_device_type : false; | 72 | return dev ? dev->type == &namespace_pmem_device_type : false; |
72 | } | 73 | } |
73 | 74 | ||
74 | static bool is_namespace_blk(struct device *dev) | 75 | static bool is_namespace_blk(const struct device *dev) |
75 | { | 76 | { |
76 | return dev ? dev->type == &namespace_blk_device_type : false; | 77 | return dev ? dev->type == &namespace_blk_device_type : false; |
77 | } | 78 | } |
78 | 79 | ||
79 | static bool is_namespace_io(struct device *dev) | 80 | static bool is_namespace_io(const struct device *dev) |
80 | { | 81 | { |
81 | return dev ? dev->type == &namespace_io_device_type : false; | 82 | return dev ? dev->type == &namespace_io_device_type : false; |
82 | } | 83 | } |
@@ -1919,6 +1920,31 @@ struct device *create_namespace_blk(struct nd_region *nd_region, | |||
1919 | return ERR_PTR(-ENXIO); | 1920 | return ERR_PTR(-ENXIO); |
1920 | } | 1921 | } |
1921 | 1922 | ||
1923 | static int cmp_dpa(const void *a, const void *b) | ||
1924 | { | ||
1925 | const struct device *dev_a = *(const struct device **) a; | ||
1926 | const struct device *dev_b = *(const struct device **) b; | ||
1927 | struct nd_namespace_blk *nsblk_a, *nsblk_b; | ||
1928 | struct nd_namespace_pmem *nspm_a, *nspm_b; | ||
1929 | |||
1930 | if (is_namespace_io(dev_a)) | ||
1931 | return 0; | ||
1932 | |||
1933 | if (is_namespace_blk(dev_a)) { | ||
1934 | nsblk_a = to_nd_namespace_blk(dev_a); | ||
1935 | nsblk_b = to_nd_namespace_blk(dev_b); | ||
1936 | |||
1937 | return memcmp(&nsblk_a->res[0]->start, &nsblk_b->res[0]->start, | ||
1938 | sizeof(resource_size_t)); | ||
1939 | } | ||
1940 | |||
1941 | nspm_a = to_nd_namespace_pmem(dev_a); | ||
1942 | nspm_b = to_nd_namespace_pmem(dev_b); | ||
1943 | |||
1944 | return memcmp(&nspm_a->nsio.res.start, &nspm_b->nsio.res.start, | ||
1945 | sizeof(resource_size_t)); | ||
1946 | } | ||
1947 | |||
1922 | static struct device **scan_labels(struct nd_region *nd_region) | 1948 | static struct device **scan_labels(struct nd_region *nd_region) |
1923 | { | 1949 | { |
1924 | struct nd_mapping *nd_mapping = &nd_region->mapping[0]; | 1950 | struct nd_mapping *nd_mapping = &nd_region->mapping[0]; |
@@ -2034,6 +2060,9 @@ static struct device **scan_labels(struct nd_region *nd_region) | |||
2034 | } | 2060 | } |
2035 | } | 2061 | } |
2036 | 2062 | ||
2063 | if (count > 1) | ||
2064 | sort(devs, count, sizeof(struct device *), cmp_dpa, NULL); | ||
2065 | |||
2037 | return devs; | 2066 | return devs; |
2038 | 2067 | ||
2039 | err: | 2068 | err: |