xref: /linux/include/linux/nd.h (revision 3ae3d67ba705c754a3c91ac009f9ce73a0e7286a)
14d88a97aSDan Williams /*
24d88a97aSDan Williams  * Copyright(c) 2013-2015 Intel Corporation. All rights reserved.
34d88a97aSDan Williams  *
44d88a97aSDan Williams  * This program is free software; you can redistribute it and/or modify
54d88a97aSDan Williams  * it under the terms of version 2 of the GNU General Public License as
64d88a97aSDan Williams  * published by the Free Software Foundation.
74d88a97aSDan Williams  *
84d88a97aSDan Williams  * This program is distributed in the hope that it will be useful, but
94d88a97aSDan Williams  * WITHOUT ANY WARRANTY; without even the implied warranty of
104d88a97aSDan Williams  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
114d88a97aSDan Williams  * General Public License for more details.
124d88a97aSDan Williams  */
134d88a97aSDan Williams #ifndef __LINUX_ND_H__
144d88a97aSDan Williams #define __LINUX_ND_H__
158c2f7e86SDan Williams #include <linux/fs.h>
164d88a97aSDan Williams #include <linux/ndctl.h>
174d88a97aSDan Williams #include <linux/device.h>
18200c79daSDan Williams #include <linux/badblocks.h>
194d88a97aSDan Williams 
2071999466SDan Williams enum nvdimm_event {
2171999466SDan Williams 	NVDIMM_REVALIDATE_POISON,
2271999466SDan Williams };
2371999466SDan Williams 
244d88a97aSDan Williams struct nd_device_driver {
254d88a97aSDan Williams 	struct device_driver drv;
264d88a97aSDan Williams 	unsigned long type;
274d88a97aSDan Williams 	int (*probe)(struct device *dev);
284d88a97aSDan Williams 	int (*remove)(struct device *dev);
29476f848aSDan Williams 	void (*shutdown)(struct device *dev);
3071999466SDan Williams 	void (*notify)(struct device *dev, enum nvdimm_event event);
314d88a97aSDan Williams };
324d88a97aSDan Williams 
334d88a97aSDan Williams static inline struct nd_device_driver *to_nd_device_driver(
344d88a97aSDan Williams 		struct device_driver *drv)
354d88a97aSDan Williams {
364d88a97aSDan Williams 	return container_of(drv, struct nd_device_driver, drv);
373d88002eSDan Williams };
383d88002eSDan Williams 
39bf9bccc1SDan Williams /**
408c2f7e86SDan Williams  * struct nd_namespace_common - core infrastructure of a namespace
418c2f7e86SDan Williams  * @force_raw: ignore other personalities for the namespace (e.g. btt)
428c2f7e86SDan Williams  * @dev: device model node
438c2f7e86SDan Williams  * @claim: when set a another personality has taken ownership of the namespace
448c2f7e86SDan Williams  * @rw_bytes: access the raw namespace capacity with byte-aligned transfers
458c2f7e86SDan Williams  */
468c2f7e86SDan Williams struct nd_namespace_common {
478c2f7e86SDan Williams 	int force_raw;
488c2f7e86SDan Williams 	struct device dev;
498c2f7e86SDan Williams 	struct device *claim;
508c2f7e86SDan Williams 	int (*rw_bytes)(struct nd_namespace_common *, resource_size_t offset,
51*3ae3d67bSVishal Verma 			void *buf, size_t size, int rw, unsigned long flags);
528c2f7e86SDan Williams };
538c2f7e86SDan Williams 
548c2f7e86SDan Williams static inline struct nd_namespace_common *to_ndns(struct device *dev)
558c2f7e86SDan Williams {
568c2f7e86SDan Williams 	return container_of(dev, struct nd_namespace_common, dev);
578c2f7e86SDan Williams }
588c2f7e86SDan Williams 
598c2f7e86SDan Williams /**
60200c79daSDan Williams  * struct nd_namespace_io - device representation of a persistent memory range
61bf9bccc1SDan Williams  * @dev: namespace device created by the nd region driver
62bf9bccc1SDan Williams  * @res: struct resource conversion of a NFIT SPA table
63200c79daSDan Williams  * @size: cached resource_size(@res) for fast path size checks
64200c79daSDan Williams  * @addr: virtual address to access the namespace range
65200c79daSDan Williams  * @bb: badblocks list for the namespace range
66bf9bccc1SDan Williams  */
673d88002eSDan Williams struct nd_namespace_io {
688c2f7e86SDan Williams 	struct nd_namespace_common common;
693d88002eSDan Williams 	struct resource res;
70200c79daSDan Williams 	resource_size_t size;
717a9eb206SDan Williams 	void *addr;
72200c79daSDan Williams 	struct badblocks bb;
733d88002eSDan Williams };
743d88002eSDan Williams 
75bf9bccc1SDan Williams /**
76bf9bccc1SDan Williams  * struct nd_namespace_pmem - namespace device for dimm-backed interleaved memory
77bf9bccc1SDan Williams  * @nsio: device and system physical address range to drive
78bf9bccc1SDan Williams  * @alt_name: namespace name supplied in the dimm label
79bf9bccc1SDan Williams  * @uuid: namespace name supplied in the dimm label
800e3b0d12SDan Williams  * @id: ida allocated id
81bf9bccc1SDan Williams  */
82bf9bccc1SDan Williams struct nd_namespace_pmem {
83bf9bccc1SDan Williams 	struct nd_namespace_io nsio;
84bf9bccc1SDan Williams 	char *alt_name;
85bf9bccc1SDan Williams 	u8 *uuid;
860e3b0d12SDan Williams 	int id;
87bf9bccc1SDan Williams };
88bf9bccc1SDan Williams 
891b40e09aSDan Williams /**
901b40e09aSDan Williams  * struct nd_namespace_blk - namespace for dimm-bounded persistent memory
911b40e09aSDan Williams  * @alt_name: namespace name supplied in the dimm label
921b40e09aSDan Williams  * @uuid: namespace name supplied in the dimm label
931b40e09aSDan Williams  * @id: ida allocated id
941b40e09aSDan Williams  * @lbasize: blk namespaces have a native sector size when btt not present
959d90725dSDan Williams  * @size: sum of all the resource ranges allocated to this namespace
961b40e09aSDan Williams  * @num_resources: number of dpa extents to claim
971b40e09aSDan Williams  * @res: discontiguous dpa extents for given dimm
981b40e09aSDan Williams  */
991b40e09aSDan Williams struct nd_namespace_blk {
1008c2f7e86SDan Williams 	struct nd_namespace_common common;
1011b40e09aSDan Williams 	char *alt_name;
1021b40e09aSDan Williams 	u8 *uuid;
1031b40e09aSDan Williams 	int id;
1041b40e09aSDan Williams 	unsigned long lbasize;
1059d90725dSDan Williams 	resource_size_t size;
1061b40e09aSDan Williams 	int num_resources;
1071b40e09aSDan Williams 	struct resource **res;
1081b40e09aSDan Williams };
1091b40e09aSDan Williams 
1106ff3e912SDan Williams static inline struct nd_namespace_io *to_nd_namespace_io(const struct device *dev)
1113d88002eSDan Williams {
1128c2f7e86SDan Williams 	return container_of(dev, struct nd_namespace_io, common.dev);
1134d88a97aSDan Williams }
1144d88a97aSDan Williams 
1156ff3e912SDan Williams static inline struct nd_namespace_pmem *to_nd_namespace_pmem(const struct device *dev)
116bf9bccc1SDan Williams {
117bf9bccc1SDan Williams 	struct nd_namespace_io *nsio = to_nd_namespace_io(dev);
118bf9bccc1SDan Williams 
119bf9bccc1SDan Williams 	return container_of(nsio, struct nd_namespace_pmem, nsio);
120bf9bccc1SDan Williams }
121bf9bccc1SDan Williams 
1226ff3e912SDan Williams static inline struct nd_namespace_blk *to_nd_namespace_blk(const struct device *dev)
1231b40e09aSDan Williams {
1248c2f7e86SDan Williams 	return container_of(dev, struct nd_namespace_blk, common.dev);
1258c2f7e86SDan Williams }
1268c2f7e86SDan Williams 
1278c2f7e86SDan Williams /**
1288c2f7e86SDan Williams  * nvdimm_read_bytes() - synchronously read bytes from an nvdimm namespace
1298c2f7e86SDan Williams  * @ndns: device to read
1308c2f7e86SDan Williams  * @offset: namespace-relative starting offset
1318c2f7e86SDan Williams  * @buf: buffer to fill
1328c2f7e86SDan Williams  * @size: transfer length
1338c2f7e86SDan Williams  *
1348c2f7e86SDan Williams  * @buf is up-to-date upon return from this routine.
1358c2f7e86SDan Williams  */
1368c2f7e86SDan Williams static inline int nvdimm_read_bytes(struct nd_namespace_common *ndns,
137*3ae3d67bSVishal Verma 		resource_size_t offset, void *buf, size_t size,
138*3ae3d67bSVishal Verma 		unsigned long flags)
1398c2f7e86SDan Williams {
140*3ae3d67bSVishal Verma 	return ndns->rw_bytes(ndns, offset, buf, size, READ, flags);
1418c2f7e86SDan Williams }
1428c2f7e86SDan Williams 
1438c2f7e86SDan Williams /**
1448c2f7e86SDan Williams  * nvdimm_write_bytes() - synchronously write bytes to an nvdimm namespace
1458c2f7e86SDan Williams  * @ndns: device to read
1468c2f7e86SDan Williams  * @offset: namespace-relative starting offset
1478c2f7e86SDan Williams  * @buf: buffer to drain
1488c2f7e86SDan Williams  * @size: transfer length
1498c2f7e86SDan Williams  *
1508c2f7e86SDan Williams  * NVDIMM Namepaces disks do not implement sectors internally.  Depending on
1518c2f7e86SDan Williams  * the @ndns, the contents of @buf may be in cpu cache, platform buffers,
1528c2f7e86SDan Williams  * or on backing memory media upon return from this routine.  Flushing
1538c2f7e86SDan Williams  * to media is handled internal to the @ndns driver, if at all.
1548c2f7e86SDan Williams  */
1558c2f7e86SDan Williams static inline int nvdimm_write_bytes(struct nd_namespace_common *ndns,
156*3ae3d67bSVishal Verma 		resource_size_t offset, void *buf, size_t size,
157*3ae3d67bSVishal Verma 		unsigned long flags)
1588c2f7e86SDan Williams {
159*3ae3d67bSVishal Verma 	return ndns->rw_bytes(ndns, offset, buf, size, WRITE, flags);
1601b40e09aSDan Williams }
1611b40e09aSDan Williams 
1624d88a97aSDan Williams #define MODULE_ALIAS_ND_DEVICE(type) \
1634d88a97aSDan Williams 	MODULE_ALIAS("nd:t" __stringify(type) "*")
1644d88a97aSDan Williams #define ND_DEVICE_MODALIAS_FMT "nd:t%d"
1654d88a97aSDan Williams 
16671999466SDan Williams struct nd_region;
16771999466SDan Williams void nvdimm_region_notify(struct nd_region *nd_region, enum nvdimm_event event);
1684d88a97aSDan Williams int __must_check __nd_driver_register(struct nd_device_driver *nd_drv,
1694d88a97aSDan Williams 		struct module *module, const char *mod_name);
1704d88a97aSDan Williams #define nd_driver_register(driver) \
1714d88a97aSDan Williams 	__nd_driver_register(driver, THIS_MODULE, KBUILD_MODNAME)
1724d88a97aSDan Williams #endif /* __LINUX_ND_H__ */
173