paul@359 | 1 | = Paging = |
paul@359 | 2 | |
paul@359 | 3 | Within filesystem servers, a number of abstractions are combined to support |
paul@359 | 4 | [[FilesystemAccess|access to filesystem content]] through paging: the delivery |
paul@359 | 5 | of content to clients in mapped memory. |
paul@359 | 6 | |
paul@359 | 7 | The general paging mechanism used to support paging is depicted below. |
paul@359 | 8 | |
paul@359 | 9 | ######## A graph showing the general paging mechanism |
paul@359 | 10 | |
paul@359 | 11 | {{{#!graphviz |
paul@359 | 12 | #format svg |
paul@359 | 13 | #transform notugly |
paul@359 | 14 | digraph paging { |
paul@359 | 15 | node [fontsize="12.0",fontname="sans-serif",shape=box]; |
paul@359 | 16 | edge [fontsize="12.0",fontname="sans-serif"]; |
paul@359 | 17 | rankdir=LR; |
paul@359 | 18 | |
paul@359 | 19 | subgraph { |
paul@359 | 20 | rank=same; |
paul@359 | 21 | |
paul@359 | 22 | Pager_note [shape=note,style=filled,fillcolor=gold,label="Provides\nfilesystem\ncontent"]; |
paul@359 | 23 | Pager; |
paul@359 | 24 | |
paul@359 | 25 | Pager_note -> Pager [dir=none,style=dotted]; |
paul@359 | 26 | } |
paul@359 | 27 | |
paul@359 | 28 | subgraph { |
paul@359 | 29 | rank=same; |
paul@359 | 30 | |
paul@359 | 31 | PageMapper_note [shape=note,style=filled,fillcolor=gold,label="Provides\npopulated\nfile pages"]; |
paul@359 | 32 | PageMapper; |
paul@359 | 33 | |
paul@359 | 34 | PageMapper_note -> PageMapper [dir=none,style=dotted]; |
paul@359 | 35 | } |
paul@359 | 36 | |
paul@359 | 37 | subgraph { |
paul@359 | 38 | rank=same; |
paul@359 | 39 | |
paul@359 | 40 | Accessor_note [shape=note,style=filled,fillcolor=gold,label="Populates\nfile pages"]; |
paul@359 | 41 | Accessor; |
paul@359 | 42 | |
paul@359 | 43 | Accessor_note -> Accessor [dir=none,style=dotted]; |
paul@359 | 44 | } |
paul@359 | 45 | |
paul@359 | 46 | AccessMap [shape=record,label="<head> AccessMap | |
paul@359 | 47 | { offset-0 |<fp0> flexpage-0 } | ... | |
paul@359 | 48 | { offset-n |<fpn> flexpage-n } | ..."]; |
paul@359 | 49 | |
paul@359 | 50 | subgraph { |
paul@359 | 51 | rank=same; |
paul@359 | 52 | |
paul@359 | 53 | Pages_note [shape=note,style=filled,fillcolor=gold,label="Provides\nmemory\npages"]; |
paul@359 | 54 | Pages; |
paul@359 | 55 | |
paul@359 | 56 | Pages_note -> Pages [dir=none,style=dotted]; |
paul@359 | 57 | } |
paul@359 | 58 | |
paul@359 | 59 | PageQueue [shape=record,label="<head> PageQueue | |
paul@359 | 60 | { owner-0 |<fp0> flexpage-0 } | ... | |
paul@359 | 61 | { owner-N |<fpN> flexpage-N } | <end> ..."]; |
paul@359 | 62 | |
paul@359 | 63 | Flexpage_offset_n [shape=record,label="<head> Flexpage | |
paul@359 | 64 | offset | size |<r> region"]; |
paul@359 | 65 | |
paul@359 | 66 | subgraph { |
paul@359 | 67 | rank=same; |
paul@359 | 68 | |
paul@359 | 69 | Memory_note [shape=note,style=filled,fillcolor=gold,label="Allocates\nmemory\nregions"]; |
paul@359 | 70 | Memory; |
paul@359 | 71 | |
paul@359 | 72 | Memory_note -> Memory [dir=none,style=dotted]; |
paul@359 | 73 | } |
paul@359 | 74 | |
paul@359 | 75 | Region; |
paul@359 | 76 | |
paul@359 | 77 | /* Relationships. */ |
paul@359 | 78 | |
paul@359 | 79 | PageMapper -> Accessor; |
paul@359 | 80 | PageMapper -> AccessMap:head; |
paul@359 | 81 | Pager -> PageMapper -> Pages; |
paul@359 | 82 | Pages -> Memory; |
paul@359 | 83 | Pages -> PageQueue:head; |
paul@359 | 84 | AccessMap:fpn -> Flexpage_offset_n:head; |
paul@359 | 85 | PageQueue:fpN -> Flexpage_offset_n:head; |
paul@359 | 86 | Flexpage_offset_n:r -> Region; |
paul@359 | 87 | } |
paul@359 | 88 | }}} |
paul@359 | 89 | |
paul@359 | 90 | ######## |
paul@359 | 91 | |
paul@359 | 92 | A [[FilesystemAccess#Pager|Pager]], being a resource that provides filesystem |
paul@359 | 93 | content to clients for a particular file, requests pages from the PageMapper, |
paul@359 | 94 | itself having the role of supplying populated pages of content from the given |
paul@359 | 95 | file. The PageMapper relies on the AccessMap to discover existing pages for |
paul@359 | 96 | any accessed region of a file, involving the Pages object (or page collection) |
paul@359 | 97 | to obtain new memory pages where existing pages are not available or are no |
paul@359 | 98 | longer valid, and requesting the population of such pages through use of the |
paul@359 | 99 | associated Accessor for the file concerned. |
paul@359 | 100 | |
paul@359 | 101 | The Pages object may either obtain new memory pages from a Memory object or |
paul@359 | 102 | reclaim (or recycle) existing pages from a PageQueue, this recording all pages |
paul@359 | 103 | that have been populated and supplied to clients. Since it may be desirable to |
paul@359 | 104 | limit the number of pages employed to satisfy file access operations, the |
paul@359 | 105 | PageQueue provides a kind of lending mechanism: pages are issued to clients |
paul@359 | 106 | and then added to the end of the queue; where no new page can be supplied by a |
paul@359 | 107 | Memory object, the issued page at the head of the queue is obtained for |
paul@359 | 108 | recycling; ultimately, an issued page will remain valid for its user (the |
paul@359 | 109 | client accessing its contents) until all pages in front of it in the queue are |
paul@359 | 110 | themselves recycled and it is then removed from the queue for recycling. |