forked from torvalds/linux
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
For the purpose of communicating the optional presence of a 'struct page' for the pfn returned from ->direct_access(), introduce a type that encapsulates a page-frame-number plus flags. These flags contain the historical "page_link" encoding for a scatterlist entry, but can also denote "device memory". Where "device memory" is a set of pfns that are not part of the kernel's linear mapping by default, but are accessed via the same memory controller as ram. The motivation for this new type is large capacity persistent memory that needs struct page entries in the 'memmap' to support 3rd party DMA (i.e. O_DIRECT I/O with a persistent memory source/target). However, we also need it in support of maintaining a list of mapped inodes which need to be unmapped at driver teardown or freeze_bdev() time. Signed-off-by: Dan Williams <[email protected]> Cc: Christoph Hellwig <[email protected]> Cc: Dave Hansen <[email protected]> Cc: Ross Zwisler <[email protected]> Signed-off-by: Andrew Morton <[email protected]> Signed-off-by: Linus Torvalds <[email protected]>
- Loading branch information
Showing
9 changed files
with
116 additions
and
23 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
#ifndef _LINUX_PFN_T_H_ | ||
#define _LINUX_PFN_T_H_ | ||
#include <linux/mm.h> | ||
|
||
/* | ||
* PFN_FLAGS_MASK - mask of all the possible valid pfn_t flags | ||
* PFN_SG_CHAIN - pfn is a pointer to the next scatterlist entry | ||
* PFN_SG_LAST - pfn references a page and is the last scatterlist entry | ||
* PFN_DEV - pfn is not covered by system memmap by default | ||
* PFN_MAP - pfn has a dynamic page mapping established by a device driver | ||
*/ | ||
#define PFN_FLAGS_MASK (((unsigned long) ~PAGE_MASK) \ | ||
<< (BITS_PER_LONG - PAGE_SHIFT)) | ||
#define PFN_SG_CHAIN (1UL << (BITS_PER_LONG - 1)) | ||
#define PFN_SG_LAST (1UL << (BITS_PER_LONG - 2)) | ||
#define PFN_DEV (1UL << (BITS_PER_LONG - 3)) | ||
#define PFN_MAP (1UL << (BITS_PER_LONG - 4)) | ||
|
||
static inline pfn_t __pfn_to_pfn_t(unsigned long pfn, unsigned long flags) | ||
{ | ||
pfn_t pfn_t = { .val = pfn | (flags & PFN_FLAGS_MASK), }; | ||
|
||
return pfn_t; | ||
} | ||
|
||
/* a default pfn to pfn_t conversion assumes that @pfn is pfn_valid() */ | ||
static inline pfn_t pfn_to_pfn_t(unsigned long pfn) | ||
{ | ||
return __pfn_to_pfn_t(pfn, 0); | ||
} | ||
|
||
extern pfn_t phys_to_pfn_t(dma_addr_t addr, unsigned long flags); | ||
|
||
static inline bool pfn_t_has_page(pfn_t pfn) | ||
{ | ||
return (pfn.val & PFN_MAP) == PFN_MAP || (pfn.val & PFN_DEV) == 0; | ||
} | ||
|
||
static inline unsigned long pfn_t_to_pfn(pfn_t pfn) | ||
{ | ||
return pfn.val & ~PFN_FLAGS_MASK; | ||
} | ||
|
||
static inline struct page *pfn_t_to_page(pfn_t pfn) | ||
{ | ||
if (pfn_t_has_page(pfn)) | ||
return pfn_to_page(pfn_t_to_pfn(pfn)); | ||
return NULL; | ||
} | ||
|
||
static inline dma_addr_t pfn_t_to_phys(pfn_t pfn) | ||
{ | ||
return PFN_PHYS(pfn_t_to_pfn(pfn)); | ||
} | ||
|
||
static inline void *pfn_t_to_virt(pfn_t pfn) | ||
{ | ||
if (pfn_t_has_page(pfn)) | ||
return __va(pfn_t_to_phys(pfn)); | ||
return NULL; | ||
} | ||
|
||
static inline pfn_t page_to_pfn_t(struct page *page) | ||
{ | ||
return pfn_to_pfn_t(page_to_pfn(page)); | ||
} | ||
#endif /* _LINUX_PFN_T_H_ */ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters